"""
Test lldb breakpoint command add/list/delete.
"""


import lldb
from lldbsuite.test.decorators import *
from lldbsuite.test.lldbtest import *
from lldbsuite.test import lldbutil
import json
import os
import side_effect


class BreakpointCommandTestCase(TestBase):
    NO_DEBUG_INFO_TESTCASE = True

    @expectedFailureAll(oslist=["windows"], bugnumber="llvm.org/pr24528")
    def test_breakpoint_command_sequence(self):
        """Test a sequence of breakpoint command add, list, and delete."""
        self.build()
        self.breakpoint_command_sequence()

    @skipIf(oslist=["windows"], bugnumber="llvm.org/pr44431")
    def test_script_parameters(self):
        """Test a sequence of breakpoint command add, list, and delete."""
        self.build()
        self.breakpoint_command_script_parameters()

    def test_commands_on_creation(self):
        self.build()
        self.breakpoint_commands_on_creation()

    @skipIf(oslist=["windows"])
    @no_debug_info_test
    def test_breakpoints_with_relative_path_line_tables(self):
        """
        Test that we can set breakpoints using a full or partial path when
        line tables in the debug information has relative paths where the
        relative path is either fully contained in the specified path, or if
        the specified path also a relative path that is shorter than the
        path in the debug info.

        The "relative.yaml" contains a line table that is:

        Line table for a/b/c/main.cpp in `a.out
        0x0000000100003f94: a/b/c/main.cpp:1
        0x0000000100003fb0: a/b/c/main.cpp:2:3
        0x0000000100003fb8: a/b/c/main.cpp:2:3

        So the line table contains relative paths. We should be able to set
        breakpoints with any source path that matches this path which
        includes paths that are longer than "a/b/c/main.cpp", but also any
        relative path that is shorter than this while all specified relative
        path components still match.
        """
        src_dir = self.getSourceDir()
        yaml_path = os.path.join(src_dir, "relative.yaml")
        yaml_base, ext = os.path.splitext(yaml_path)
        obj_path = self.getBuildArtifact("a.out")
        self.yaml2obj(yaml_path, obj_path)

        # Create a target with the object file we just created from YAML
        target = self.dbg.CreateTarget(obj_path)
        # We now have debug information with line table paths that start are
        # "./a/b/c/main.cpp".

        # Make sure that all of the following paths create a breakpoint
        # successfully. We have paths that are longer than our path, and also
        # that are shorter where all relative directories still match.
        valid_paths = [
            "/x/a/b/c/main.cpp",
            "/x/y/a/b/c/main.cpp",
            "./x/y/a/b/c/main.cpp",
            "x/y/a/b/c/main.cpp",
            "./y/a/b/c/main.cpp",
            "y/a/b/c/main.cpp",
            "./a/b/c/main.cpp",
            "a/b/c/main.cpp",
            "./b/c/main.cpp",
            "b/c/main.cpp",
            "./c/main.cpp",
            "c/main.cpp",
            "./main.cpp",
            "main.cpp",
        ]
        for path in valid_paths:
            bkpt = target.BreakpointCreateByLocation(path, 2)
            self.assertGreater(
                bkpt.GetNumLocations(),
                0,
                'Couldn\'t resolve breakpoint using full path "%s" in executate "%s" with '
                "debug info that has relative path with matching suffix"
                % (path, self.getBuildArtifact("a.out")),
            )
        invalid_paths = [
            "/x/b/c/main.cpp",
            "/x/c/main.cpp",
            "/x/main.cpp",
            "./x/y/a/d/c/main.cpp",
        ]
        # Reset source map.
        self.runCmd("settings clear target.source-map")
        for path in invalid_paths:
            bkpt = target.BreakpointCreateByLocation(path, 2)
            self.assertEqual(
                bkpt.GetNumLocations(),
                0,
                'Incorrectly resolved a breakpoint using full path "%s" with '
                "debug info that has relative path with matching suffix" % (path),
            )

    @no_debug_info_test
    def test_breakpoints_with_bad_aranges(self):
        """
        Test that we can set breakpoints in a file that has an invalid
        .debug_aranges. Older versions of LLDB would find a line entry
        in the line table and then would use the start address of the line
        entry to do an address lookup on the entry from the line table. If
        this address to symbol context lookup would fail, due to a bad
        .debug_aranges, it would cause the breakpoint to not get resolved.
        Verify that even in these conditions we are able to resolve a
        breakpoint.

        The "bad_aranges.yaml" contains a line table that is:

        Line table for /tmp/ab/main.cpp in `a.out
        0x0000000100003f94: /tmp/ab/main.cpp:1
        0x0000000100003fb0: /tmp/ab/main.cpp:2:3
        0x0000000100003fb8: /tmp/ab/main.cpp:2:3

        The .debug_aranges has one range for this compile unit that is
        invalid: [0x0000000200003f94-0x0000000200003fb8). This will cause
        the resolving of the addresses to fail.
        """
        src_dir = self.getSourceDir()
        yaml_path = os.path.join(src_dir, "bad_aranges.yaml")
        yaml_base, ext = os.path.splitext(yaml_path)
        obj_path = self.getBuildArtifact("a.out")
        self.yaml2obj(yaml_path, obj_path)

        # Create a target with the object file we just created from YAML
        target = self.dbg.CreateTarget(obj_path)
        src_path = "/tmp/ab/main.cpp"
        bkpt = target.BreakpointCreateByLocation(src_path, 2)
        self.assertGreater(
            bkpt.GetNumLocations(),
            0,
            'Couldn\'t resolve breakpoint using "%s" in executate "%s" with '
            "debug info that has a bad .debug_aranges section"
            % (src_path, self.getBuildArtifact("a.out")),
        )

    def setUp(self):
        # Call super's setUp().
        TestBase.setUp(self)
        # Find the line number to break inside main().
        self.line = line_number("main.c", "// Set break point at this line.")
        # disable "There is a running process, kill it and restart?" prompt
        self.runCmd("settings set auto-confirm true")
        self.addTearDownHook(lambda: self.runCmd("settings clear auto-confirm"))

    def test_delete_all_breakpoints(self):
        """Test that deleting all breakpoints works."""
        self.build()
        exe = self.getBuildArtifact("a.out")
        self.runCmd("file " + exe, CURRENT_EXECUTABLE_SET)

        lldbutil.run_break_set_by_symbol(self, "main")
        lldbutil.run_break_set_by_file_and_line(
            self, "main.c", self.line, num_expected_locations=1, loc_exact=True
        )

        self.runCmd("run", RUN_SUCCEEDED)

        self.runCmd("breakpoint delete")
        self.runCmd("process continue")
        self.expect(
            "process status",
            PROCESS_STOPPED,
            patterns=["Process .* exited with status = 0"],
        )

    def breakpoint_command_sequence(self):
        """Test a sequence of breakpoint command add, list, and delete."""
        exe = self.getBuildArtifact("a.out")
        self.runCmd("file " + exe, CURRENT_EXECUTABLE_SET)

        # Add three breakpoints on the same line.  The first time we don't specify the file,
        # since the default file is the one containing main:
        lldbutil.run_break_set_by_file_and_line(
            self, None, self.line, num_expected_locations=1, loc_exact=True
        )
        lldbutil.run_break_set_by_file_and_line(
            self, "main.c", self.line, num_expected_locations=1, loc_exact=True
        )
        lldbutil.run_break_set_by_file_and_line(
            self, "main.c", self.line, num_expected_locations=1, loc_exact=True
        )
        # Breakpoint 4 - set at the same location as breakpoint 1 to test
        # setting breakpoint commands on two breakpoints at a time
        lldbutil.run_break_set_by_file_and_line(
            self, None, self.line, num_expected_locations=1, loc_exact=True
        )
        # Make sure relative path source breakpoints work as expected. We test
        # with partial paths with and without "./" prefixes.
        lldbutil.run_break_set_by_file_and_line(
            self, "./main.c", self.line, num_expected_locations=1, loc_exact=True
        )
        lldbutil.run_break_set_by_file_and_line(
            self,
            "breakpoint_command/main.c",
            self.line,
            num_expected_locations=1,
            loc_exact=True,
        )
        lldbutil.run_break_set_by_file_and_line(
            self,
            "./breakpoint_command/main.c",
            self.line,
            num_expected_locations=1,
            loc_exact=True,
        )
        lldbutil.run_break_set_by_file_and_line(
            self,
            "breakpoint/breakpoint_command/main.c",
            self.line,
            num_expected_locations=1,
            loc_exact=True,
        )
        lldbutil.run_break_set_by_file_and_line(
            self,
            "./breakpoint/breakpoint_command/main.c",
            self.line,
            num_expected_locations=1,
            loc_exact=True,
        )
        # Test relative breakpoints with incorrect paths and make sure we get
        # no breakpoint locations
        lldbutil.run_break_set_by_file_and_line(
            self, "invalid/main.c", self.line, num_expected_locations=0, loc_exact=True
        )
        lldbutil.run_break_set_by_file_and_line(
            self,
            "./invalid/main.c",
            self.line,
            num_expected_locations=0,
            loc_exact=True,
        )
        # Now add callbacks for the breakpoints just created.
        self.runCmd(
            "breakpoint command add -s command -o 'frame variable --show-types --scope' 1 4"
        )
        self.runCmd(
            "breakpoint command add -s python -o 'import side_effect; side_effect.one_liner = \"one liner was here\"' 2"
        )

        import side_effect

        self.runCmd("command script import --allow-reload ./bktptcmd.py")

        self.runCmd("breakpoint command add --python-function bktptcmd.function 3")

        # Check that the breakpoint commands are correctly set.

        # The breakpoint list now only contains breakpoint 1.
        self.expect(
            "breakpoint list",
            "Breakpoints 1 & 2 created",
            substrs=[
                "2: file = 'main.c', line = %d, exact_match = 0, locations = 1"
                % self.line
            ],
            patterns=[
                "1: file = '.*main.c', line = %d, exact_match = 0, locations = 1"
                % self.line
            ],
        )

        self.expect(
            "breakpoint list -f",
            "Breakpoints 1 & 2 created",
            substrs=[
                "2: file = 'main.c', line = %d, exact_match = 0, locations = 1"
                % self.line
            ],
            patterns=[
                "1: file = '.*main.c', line = %d, exact_match = 0, locations = 1"
                % self.line,
                "1.1: .+at main.c:%d:?[0-9]*, .+unresolved, hit count = 0" % self.line,
                "2.1: .+at main.c:%d:?[0-9]*, .+unresolved, hit count = 0" % self.line,
            ],
        )

        self.expect(
            "breakpoint command list 1",
            "Breakpoint 1 command ok",
            substrs=["Breakpoint commands:", "frame variable --show-types --scope"],
        )
        self.expect(
            "breakpoint command list 2",
            "Breakpoint 2 command ok",
            substrs=[
                "Breakpoint commands (Python):",
                "import side_effect",
                "side_effect.one_liner",
            ],
        )
        self.expect(
            "breakpoint command list 3",
            "Breakpoint 3 command ok",
            substrs=[
                "Breakpoint commands (Python):",
                "bktptcmd.function(frame, bp_loc, internal_dict)",
            ],
        )

        self.expect(
            "breakpoint command list 4",
            "Breakpoint 4 command ok",
            substrs=["Breakpoint commands:", "frame variable --show-types --scope"],
        )

        self.runCmd("breakpoint delete 4")

        # Next lets try some other breakpoint kinds.  First break with a regular expression
        # and then specify only one file.  The first time we should get two locations,
        # the second time only one:

        lldbutil.run_break_set_by_regexp(
            self, r"._MyFunction", num_expected_locations=2
        )

        lldbutil.run_break_set_by_regexp(
            self, r"._MyFunction", extra_options="-f a.c", num_expected_locations=1
        )

        lldbutil.run_break_set_by_regexp(
            self,
            r"._MyFunction",
            extra_options="-f a.c -f b.c",
            num_expected_locations=2,
        )

        # Now try a source regex breakpoint:
        lldbutil.run_break_set_by_source_regexp(
            self,
            r"is about to return [12]0",
            extra_options="-f a.c -f b.c",
            num_expected_locations=2,
        )

        lldbutil.run_break_set_by_source_regexp(
            self,
            r"is about to return [12]0",
            extra_options="-f a.c",
            num_expected_locations=1,
        )

        # Reset our canary variables and run the program.
        side_effect.one_liner = None
        side_effect.bktptcmd = None
        self.runCmd("run", RUN_SUCCEEDED)

        # Check the value of canary variables.
        self.assertEqual("one liner was here", side_effect.one_liner)
        self.assertEqual("function was here", side_effect.bktptcmd)

        # Finish the program.
        self.runCmd("process continue")

        # Remove the breakpoint command associated with breakpoint 1.
        self.runCmd("breakpoint command delete 1")

        # Remove breakpoint 2.
        self.runCmd("breakpoint delete 2")

        self.expect(
            "breakpoint command list 1",
            startstr="Breakpoint 1 does not have an associated command.",
        )
        self.expect(
            "breakpoint command list 2",
            error=True,
            startstr="error: '2' is not a currently valid breakpoint ID.",
        )

        # The breakpoint list now only contains breakpoint 1.
        self.expect(
            "breakpoint list -f",
            "Breakpoint 1 exists",
            patterns=[
                "1: file = '.*main.c', line = %d, exact_match = 0, locations = 1, resolved = 1"
                % self.line,
                "hit count = 1",
            ],
        )

        # Not breakpoint 2.
        self.expect(
            "breakpoint list -f",
            "No more breakpoint 2",
            matching=False,
            substrs=[
                "2: file = 'main.c', line = %d, exact_match = 0, locations = 1, resolved = 1"
                % self.line
            ],
        )

        # Run the program again, with breakpoint 1 remaining.
        self.runCmd("run", RUN_SUCCEEDED)

        # We should be stopped again due to breakpoint 1.

        # The stop reason of the thread should be breakpoint.
        self.expect(
            "thread list",
            STOPPED_DUE_TO_BREAKPOINT,
            substrs=["stopped", "stop reason = breakpoint"],
        )

        # The breakpoint should have a hit count of 1, since we reset counts
        # for each run.
        lldbutil.check_breakpoint(self, bpno=1, expected_hit_count=1)

    def breakpoint_command_script_parameters(self):
        """Test that the frame and breakpoint location are being properly passed to the script breakpoint command function."""
        exe = self.getBuildArtifact("a.out")
        self.runCmd("file " + exe, CURRENT_EXECUTABLE_SET)

        # Add a breakpoint.
        lldbutil.run_break_set_by_file_and_line(
            self, "main.c", self.line, num_expected_locations=1, loc_exact=True
        )

        # Now add callbacks for the breakpoints just created.
        self.runCmd(
            "breakpoint command add -s python -o 'import side_effect; side_effect.frame = str(frame); side_effect.bp_loc = str(bp_loc)' 1"
        )

        # Reset canary variables and run.
        side_effect.frame = None
        side_effect.bp_loc = None
        self.runCmd("run", RUN_SUCCEEDED)

        self.expect(side_effect.frame, exe=False, startstr="frame #0:")
        self.expect(
            side_effect.bp_loc,
            exe=False,
            patterns=["1.* where = .*main .* resolved,( hardware,)? hit count = 1"],
        )

    def breakpoint_commands_on_creation(self):
        """Test that setting breakpoint commands when creating the breakpoint works"""
        target = self.createTestTarget()

        # Add a breakpoint.
        lldbutil.run_break_set_by_file_and_line(
            self,
            "main.c",
            self.line,
            num_expected_locations=1,
            loc_exact=True,
            extra_options='-C bt -C "thread list" -C continue',
        )

        bkpt = target.FindBreakpointByID(1)
        self.assertTrue(bkpt.IsValid(), "Couldn't find breakpoint 1")
        com_list = lldb.SBStringList()
        bkpt.GetCommandLineCommands(com_list)
        self.assertEqual(com_list.GetSize(), 3, "Got the wrong number of commands")
        self.assertEqual(com_list.GetStringAtIndex(0), "bt", "First bt")
        self.assertEqual(
            com_list.GetStringAtIndex(1), "thread list", "Next thread list"
        )
        self.assertEqual(com_list.GetStringAtIndex(2), "continue", "Last continue")

    def test_add_commands_by_breakpoint_name(self):
        """Make sure that when you specify a breakpoint name to "break command add"
        it gets added to all the breakpoints marked with that name."""
        self.build()
        target = self.createTestTarget()

        bp_ids = []
        bp_names = ["main", "not_here", "main"]
        for bp_name in bp_names:
            bp = target.BreakpointCreateByName(bp_name)
            bp.AddName("MyBKPTS")
            bp_ids.append(bp.GetID())
        # First do it with a script one-liner:
        self.runCmd("breakpoint command add -s py -o 'print(\"some command\")' MyBKPTS")
        for id in bp_ids:
            self.expect(
                "breakpoint command list {0}".format(id), patterns=["some command"]
            )
        # Now do the same thing with a python function:
        import side_effect

        self.runCmd("command script import --allow-reload ./bktptcmd.py")

        self.runCmd(
            "breakpoint command add --python-function bktptcmd.function MyBKPTS"
        )
        for id in bp_ids:
            self.expect(
                "breakpoint command list {0}".format(id), patterns=["bktptcmd.function"]
            )

    def test_breakpoint_delete_disabled(self):
        """Test 'break delete --disabled' works"""
        self.build()
        target = self.createTestTarget()

        bp_1 = target.BreakpointCreateByName("main")
        bp_2 = target.BreakpointCreateByName("not_here")
        bp_3 = target.BreakpointCreateByName("main")
        bp_3.AddName("DeleteMeNot")

        bp_1.SetEnabled(False)
        bp_3.SetEnabled(False)

        bp_id_1 = bp_1.GetID()
        bp_id_2 = bp_2.GetID()
        bp_id_3 = bp_3.GetID()

        self.runCmd("breakpoint delete --disabled DeleteMeNot")

        bp_1 = target.FindBreakpointByID(bp_id_1)
        self.assertFalse(bp_1.IsValid(), "Didn't delete disabled breakpoint 1")

        bp_2 = target.FindBreakpointByID(bp_id_2)
        self.assertTrue(bp_2.IsValid(), "Deleted enabled breakpoint 2")

        bp_3 = target.FindBreakpointByID(bp_id_3)
        self.assertTrue(
            bp_3.IsValid(), "DeleteMeNot didn't protect disabled breakpoint 3"
        )

        # Reset the first breakpoint, disable it, and do this again with no protected name:
        bp_1 = target.BreakpointCreateByName("main")

        bp_1.SetEnabled(False)

        bp_id_1 = bp_1.GetID()

        self.runCmd("breakpoint delete --disabled")

        bp_1 = target.FindBreakpointByID(bp_id_1)
        self.assertFalse(bp_1.IsValid(), "Didn't delete disabled breakpoint 1")

        bp_2 = target.FindBreakpointByID(bp_id_2)
        self.assertTrue(bp_2.IsValid(), "Deleted enabled breakpoint 2")

        bp_3 = target.FindBreakpointByID(bp_id_3)
        self.assertFalse(bp_3.IsValid(), "Didn't delete disabled breakpoint 3")

    def get_source_map_json(self):
        stream = lldb.SBStream()
        self.dbg.GetSetting("target.source-map").GetAsJSON(stream)
        return json.loads(stream.GetData())

    def verify_source_map_entry_pair(self, entry, original, replacement):
        self.assertEqual(
            entry[0], original, "source map entry 'original' does not match"
        )
        self.assertEqual(
            entry[1], replacement, "source map entry 'replacement' does not match"
        )

    def verify_source_map_deduce_statistics(self, target, expected_count):
        stream = lldb.SBStream()
        res = target.GetStatistics().GetAsJSON(stream)
        self.assertTrue(res.Success())
        debug_stats = json.loads(stream.GetData())
        self.assertIn(
            "targets",
            debug_stats,
            'Make sure the "targets" key in in target.GetStatistics()',
        )
        target_stats = debug_stats["targets"][0]
        self.assertNotEqual(target_stats, None)
        self.assertEqual(target_stats["sourceMapDeduceCount"], expected_count)

    @skipIf(oslist=["windows"])
    @no_debug_info_test
    def test_breakpoints_auto_source_map_relative(self):
        """
        Test that with target.auto-source-map-relative settings.

        The "relative.yaml" contains a line table that is:

        Line table for a/b/c/main.cpp in `a.out
        0x0000000100003f94: a/b/c/main.cpp:1
        0x0000000100003fb0: a/b/c/main.cpp:2:3
        0x0000000100003fb8: a/b/c/main.cpp:2:3
        """
        src_dir = self.getSourceDir()
        yaml_path = os.path.join(src_dir, "relative.yaml")
        yaml_base, ext = os.path.splitext(yaml_path)
        obj_path = self.getBuildArtifact("a.out")
        self.yaml2obj(yaml_path, obj_path)

        # Create a target with the object file we just created from YAML
        target = self.dbg.CreateTarget(obj_path)
        # We now have debug information with line table paths that start are
        # "./a/b/c/main.cpp".

        source_map_json = self.get_source_map_json()
        self.assertEqual(
            len(source_map_json), 0, "source map should be empty initially"
        )
        self.verify_source_map_deduce_statistics(target, 0)

        # Verify auto deduced source map when file path in debug info
        # is a suffix of request breakpoint file path
        path = "/x/y/a/b/c/main.cpp"
        bp = target.BreakpointCreateByLocation(path, 2)
        self.assertGreater(
            bp.GetNumLocations(),
            0,
            'Couldn\'t resolve breakpoint using full path "%s" in executate "%s" with '
            "debug info that has relative path with matching suffix"
            % (path, self.getBuildArtifact("a.out")),
        )

        source_map_json = self.get_source_map_json()
        self.assertEqual(len(source_map_json), 1, "source map should not be empty")
        self.verify_source_map_entry_pair(source_map_json[0], ".", "/x/y")
        self.verify_source_map_deduce_statistics(target, 1)

        # Reset source map.
        self.runCmd("settings clear target.source-map")

        # Verify source map will not auto deduced when file path of request breakpoint
        # equals the file path in debug info.
        path = "a/b/c/main.cpp"
        bp = target.BreakpointCreateByLocation(path, 2)
        self.assertGreater(
            bp.GetNumLocations(),
            0,
            'Couldn\'t resolve breakpoint using full path "%s" in executate "%s" with '
            "debug info that has relative path with matching suffix"
            % (path, self.getBuildArtifact("a.out")),
        )

        source_map_json = self.get_source_map_json()
        self.assertEqual(len(source_map_json), 0, "source map should not be deduced")

    def test_breakpoint_statistics_hitcount(self):
        """Test breakpoints statistics have hitCount field."""
        self.build()
        target = self.createTestTarget()

        lldbutil.run_break_set_by_file_and_line(
            self, "main.c", self.line, num_expected_locations=1, loc_exact=True
        )

        stream = lldb.SBStream()
        res = target.GetStatistics().GetAsJSON(stream)
        self.assertTrue(res.Success())
        debug_stats = json.loads(stream.GetData())
        self.assertIn(
            "targets",
            debug_stats,
            'Make sure the "targets" key in in target.GetStatistics()',
        )
        target_stats = debug_stats["targets"][0]
        self.assertNotEqual(target_stats, None)

        breakpoints_stats = target_stats["breakpoints"]
        self.assertNotEqual(breakpoints_stats, None)
        for breakpoint_stats in breakpoints_stats:
            self.assertIn("hitCount", breakpoint_stats)

    @skipIf(oslist=no_match(["linux"]))
    def test_break_at__dl_debug_state(self):
        """
        Test lldb is able to stop at _dl_debug_state if it is set before the
        process is launched.
        """
        self.build()
        exe = self.getBuildArtifact("a.out")
        self.runCmd("target create %s" % exe)
        bpid = lldbutil.run_break_set_by_symbol(
            self, "_dl_debug_state", num_expected_locations=-2
        )
        self.runCmd("run")
        self.assertIsNotNone(
            lldbutil.get_one_thread_stopped_at_breakpoint_id(self.process(), bpid)
        )
