"""
Test breakpoint serialization.
"""

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


class BreakpointSerialization(TestBase):
    NO_DEBUG_INFO_TESTCASE = True

    @add_test_categories(["pyapi"])
    def test_resolvers(self):
        """Use Python APIs to test that we serialize resolvers."""
        self.build()
        self.setup_targets_and_cleanup()
        self.do_check_resolvers()

    def test_filters(self):
        """Use Python APIs to test that we serialize search filters correctly."""
        self.build()
        self.setup_targets_and_cleanup()
        self.do_check_filters()

    def test_options(self):
        """Use Python APIs to test that we serialize breakpoint options correctly."""
        self.build()
        self.setup_targets_and_cleanup()
        self.do_check_options()

    def test_appending(self):
        """Use Python APIs to test that we serialize breakpoint options correctly."""
        self.build()
        self.setup_targets_and_cleanup()
        self.do_check_appending()

    def test_name_filters(self):
        """Use python APIs to test that reading in by name works correctly."""
        self.build()
        self.setup_targets_and_cleanup()
        self.do_check_names()

    def test_scripted_extra_args(self):
        self.build()
        self.setup_targets_and_cleanup()
        self.do_check_extra_args()

    def test_resolver_serialization(self):
        """Test that breakpoint resolvers contain the expected information"""
        self.build()
        self.setup_targets_and_cleanup()

        exe_path = self.getBuildArtifact("a.out")
        exe_module = self.orig_target.module["a.out"]
        self.assertTrue(
            exe_module.IsValid(), "Failed to find the executable module in target"
        )
        sym_ctx_list = exe_module.FindFunctions("main")
        self.assertTrue(sym_ctx_list.GetSize() == 1, "Unable to find function 'main'")
        sym_ctx = sym_ctx_list.GetContextAtIndex(0)
        self.assertTrue(
            sym_ctx.IsValid(), "SBSymbolContext representing function 'main' is invalid"
        )
        main_func = sym_ctx.GetFunction()
        self.assertTrue(
            main_func.IsValid(), "SBFunction representing 'main' is invalid"
        )
        main_addr = main_func.GetStartAddress()

        bkpt = self.orig_target.BreakpointCreateBySBAddress(main_addr)
        self.assertTrue(
            bkpt.IsValid(), "Could not place breakpoint on 'main' by address"
        )
        stream = lldb.SBStream()
        sd = bkpt.SerializeToStructuredData()
        sd.GetAsJSON(stream)
        serialized_data = json.loads(stream.GetData())

        self.assertIn(
            exe_path,
            serialized_data["Breakpoint"]["BKPTResolver"]["Options"]["ModuleName"],
        )

    def test_structured_data_serialization(self):
        target = self.dbg.GetDummyTarget()
        self.assertTrue(target.IsValid(), VALID_TARGET)

        interpreter = self.dbg.GetCommandInterpreter()
        result = lldb.SBCommandReturnObject()
        interpreter.HandleCommand("br set -f foo -l 42", result)
        result = lldb.SBCommandReturnObject()
        interpreter.HandleCommand("br set -c 'argc == 1' -n main", result)

        bkp1 = target.GetBreakpointAtIndex(0)
        self.assertTrue(bkp1.IsValid(), VALID_BREAKPOINT)
        stream = lldb.SBStream()
        sd = bkp1.SerializeToStructuredData()
        sd.GetAsJSON(stream)
        serialized_data = json.loads(stream.GetData())
        self.assertEqual(
            serialized_data["Breakpoint"]["BKPTResolver"]["Options"]["FileName"], "foo"
        )
        self.assertEqual(
            serialized_data["Breakpoint"]["BKPTResolver"]["Options"]["LineNumber"], 42
        )

        bkp2 = target.GetBreakpointAtIndex(1)
        self.assertTrue(bkp2.IsValid(), VALID_BREAKPOINT)
        stream = lldb.SBStream()
        sd = bkp2.SerializeToStructuredData()
        sd.GetAsJSON(stream)
        serialized_data = json.loads(stream.GetData())
        self.assertIn(
            "main",
            serialized_data["Breakpoint"]["BKPTResolver"]["Options"]["SymbolNames"],
        )
        self.assertEqual(
            serialized_data["Breakpoint"]["BKPTOptions"]["ConditionText"], "argc == 1"
        )

        invalid_bkp = lldb.SBBreakpoint()
        self.assertFalse(invalid_bkp.IsValid(), "Breakpoint should not be valid.")
        stream = lldb.SBStream()
        sd = invalid_bkp.SerializeToStructuredData()
        sd.GetAsJSON(stream)
        self.assertFalse(
            stream.GetData(), "Invalid breakpoint should have an empty structured data"
        )

    def setup_targets_and_cleanup(self):
        def cleanup():
            self.RemoveTempFile(self.bkpts_file_path)

            if self.orig_target.IsValid():
                self.dbg.DeleteTarget(self.orig_target)
                self.dbg.DeleteTarget(self.copy_target)

        self.addTearDownHook(cleanup)
        self.RemoveTempFile(self.bkpts_file_path)

        exe = self.getBuildArtifact("a.out")

        # Create the targets we are making breakpoints in and copying them to:
        self.orig_target = self.dbg.CreateTarget(exe)
        self.assertTrue(self.orig_target, VALID_TARGET)

        self.copy_target = self.dbg.CreateTarget(exe)
        self.assertTrue(self.copy_target, VALID_TARGET)

    def setUp(self):
        # Call super's setUp().
        TestBase.setUp(self)

        self.bkpts_file_path = self.getBuildArtifact("breakpoints.json")
        self.bkpts_file_spec = lldb.SBFileSpec(self.bkpts_file_path)

    def check_equivalence(self, source_bps, do_write=True):
        error = lldb.SBError()

        if do_write:
            error = self.orig_target.BreakpointsWriteToFile(
                self.bkpts_file_spec, source_bps
            )
            self.assertSuccess(error, "Failed writing breakpoints to file")

        copy_bps = lldb.SBBreakpointList(self.copy_target)
        error = self.copy_target.BreakpointsCreateFromFile(
            self.bkpts_file_spec, copy_bps
        )
        self.assertSuccess(error, "Failed reading breakpoints from file")

        num_source_bps = source_bps.GetSize()
        num_copy_bps = copy_bps.GetSize()
        self.assertEqual(
            num_source_bps,
            num_copy_bps,
            "Didn't get same number of input and output breakpoints - orig: %d copy: %d"
            % (num_source_bps, num_copy_bps),
        )

        for i in range(0, num_source_bps):
            source_bp = source_bps.GetBreakpointAtIndex(i)
            source_desc = lldb.SBStream()
            source_bp.GetDescription(source_desc, False)
            source_text = source_desc.GetData()

            # I am assuming here that the breakpoints will get written out in breakpoint ID order, and
            # read back in ditto.  That is true right now, and I can't see any reason to do it differently
            # but if we do we can go to writing the breakpoints one by one, or sniffing the descriptions to
            # see which one is which.
            copy_id = source_bp.GetID()
            copy_bp = copy_bps.FindBreakpointByID(copy_id)
            self.assertTrue(
                copy_bp.IsValid(), "Could not find copy breakpoint %d." % (copy_id)
            )

            copy_desc = lldb.SBStream()
            copy_bp.GetDescription(copy_desc, False)
            copy_text = copy_desc.GetData()

            # These two should be identical.
            self.trace("Source text for %d is %s." % (i, source_text))
            self.assertEqual(
                source_text,
                copy_text,
                "Source and dest breakpoints are not identical: \nsource: %s\ndest: %s"
                % (source_text, copy_text),
            )

    def do_check_resolvers(self):
        """Use Python APIs to check serialization of breakpoint resolvers"""

        empty_module_list = lldb.SBFileSpecList()
        empty_cu_list = lldb.SBFileSpecList()
        blubby_file_spec = lldb.SBFileSpec(
            os.path.join(self.getSourceDir(), "blubby.c")
        )

        # It isn't actually important for these purposes that these breakpoint
        # actually have locations.
        source_bps = lldb.SBBreakpointList(self.orig_target)
        source_bps.Append(self.orig_target.BreakpointCreateByLocation("blubby.c", 666))
        # Make sure we do one breakpoint right:
        self.check_equivalence(source_bps)
        source_bps.Clear()

        source_bps.Append(
            self.orig_target.BreakpointCreateByName(
                "blubby", lldb.eFunctionNameTypeAuto, empty_module_list, empty_cu_list
            )
        )
        source_bps.Append(
            self.orig_target.BreakpointCreateByName(
                "blubby", lldb.eFunctionNameTypeFull, empty_module_list, empty_cu_list
            )
        )
        source_bps.Append(
            self.orig_target.BreakpointCreateBySourceRegex(
                "dont really care", blubby_file_spec
            )
        )

        # And some number greater than one:
        self.check_equivalence(source_bps)

    def do_check_filters(self):
        """Use Python APIs to check serialization of breakpoint filters."""
        module_list = lldb.SBFileSpecList()
        module_list.Append(lldb.SBFileSpec("SomeBinary"))
        module_list.Append(lldb.SBFileSpec("SomeOtherBinary"))

        cu_list = lldb.SBFileSpecList()
        cu_list.Append(lldb.SBFileSpec("SomeCU.c"))
        cu_list.Append(lldb.SBFileSpec("AnotherCU.c"))
        cu_list.Append(lldb.SBFileSpec("ThirdCU.c"))

        blubby_file_spec = lldb.SBFileSpec(
            os.path.join(self.getSourceDir(), "blubby.c")
        )

        # It isn't actually important for these purposes that these breakpoint
        # actually have locations.
        source_bps = lldb.SBBreakpointList(self.orig_target)
        bkpt = self.orig_target.BreakpointCreateByLocation(
            blubby_file_spec, 666, 0, module_list
        )
        source_bps.Append(bkpt)

        # Make sure we do one right:
        self.check_equivalence(source_bps)
        source_bps.Clear()

        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeAuto, module_list, cu_list
        )
        source_bps.Append(bkpt)
        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeFull, module_list, cu_list
        )
        source_bps.Append(bkpt)
        bkpt = self.orig_target.BreakpointCreateBySourceRegex(
            "dont really care", blubby_file_spec
        )
        source_bps.Append(bkpt)

        # And some number greater than one:
        self.check_equivalence(source_bps)

    def do_check_options(self):
        """Use Python APIs to check serialization of breakpoint options."""

        empty_module_list = lldb.SBFileSpecList()
        empty_cu_list = lldb.SBFileSpecList()
        blubby_file_spec = lldb.SBFileSpec(
            os.path.join(self.getSourceDir(), "blubby.c")
        )

        # It isn't actually important for these purposes that these breakpoint
        # actually have locations.
        source_bps = lldb.SBBreakpointList(self.orig_target)

        bkpt = self.orig_target.BreakpointCreateByLocation(
            lldb.SBFileSpec("blubby.c"), 666, 333, 0, lldb.SBFileSpecList()
        )
        bkpt.SetEnabled(False)
        bkpt.SetOneShot(True)
        bkpt.SetThreadID(10)
        source_bps.Append(bkpt)

        # Make sure we get one right:
        self.check_equivalence(source_bps)
        source_bps.Clear()

        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeAuto, empty_module_list, empty_cu_list
        )
        bkpt.SetIgnoreCount(10)
        bkpt.SetThreadName("grubby")
        source_bps.Append(bkpt)

        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeAuto, empty_module_list, empty_cu_list
        )
        bkpt.SetCondition("gonna remove this")
        bkpt.SetCondition("")
        source_bps.Append(bkpt)

        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeFull, empty_module_list, empty_cu_list
        )
        bkpt.SetCondition("something != something_else")
        bkpt.SetQueueName("grubby")
        bkpt.AddName("FirstName")
        bkpt.AddName("SecondName")
        bkpt.SetScriptCallbackBody(
            '\tprint("I am a function that prints.")\n\tprint("I don\'t do anything else")\n'
        )
        source_bps.Append(bkpt)

        bkpt = self.orig_target.BreakpointCreateBySourceRegex(
            "dont really care", blubby_file_spec
        )
        cmd_list = lldb.SBStringList()
        cmd_list.AppendString("frame var")
        cmd_list.AppendString("thread backtrace")

        bkpt.SetCommandLineCommands(cmd_list)
        source_bps.Append(bkpt)

        self.check_equivalence(source_bps)

    def do_check_appending(self):
        """Use Python APIs to check appending to already serialized options."""

        empty_module_list = lldb.SBFileSpecList()
        empty_cu_list = lldb.SBFileSpecList()
        blubby_file_spec = lldb.SBFileSpec(
            os.path.join(self.getSourceDir(), "blubby.c")
        )

        # It isn't actually important for these purposes that these breakpoint
        # actually have locations.

        all_bps = lldb.SBBreakpointList(self.orig_target)
        source_bps = lldb.SBBreakpointList(self.orig_target)

        bkpt = self.orig_target.BreakpointCreateByLocation(
            lldb.SBFileSpec("blubby.c"), 666, 333, 0, lldb.SBFileSpecList()
        )
        bkpt.SetEnabled(False)
        bkpt.SetOneShot(True)
        bkpt.SetThreadID(10)
        source_bps.Append(bkpt)
        all_bps.Append(bkpt)

        error = lldb.SBError()
        error = self.orig_target.BreakpointsWriteToFile(
            self.bkpts_file_spec, source_bps
        )
        self.assertSuccess(error, "Failed writing breakpoints to file")

        source_bps.Clear()

        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeAuto, empty_module_list, empty_cu_list
        )
        bkpt.SetIgnoreCount(10)
        bkpt.SetThreadName("grubby")
        source_bps.Append(bkpt)
        all_bps.Append(bkpt)

        bkpt = self.orig_target.BreakpointCreateByName(
            "blubby", lldb.eFunctionNameTypeFull, empty_module_list, empty_cu_list
        )
        bkpt.SetCondition("something != something_else")
        bkpt.SetQueueName("grubby")
        bkpt.AddName("FirstName")
        bkpt.AddName("SecondName")

        source_bps.Append(bkpt)
        all_bps.Append(bkpt)

        error = self.orig_target.BreakpointsWriteToFile(
            self.bkpts_file_spec, source_bps, True
        )
        self.assertSuccess(error, "Failed appending breakpoints to file")

        self.check_equivalence(all_bps)

    def do_check_names(self):
        bkpt = self.orig_target.BreakpointCreateByLocation(
            lldb.SBFileSpec("blubby.c"), 666, 333, 0, lldb.SBFileSpecList()
        )
        good_bkpt_name = "GoodBreakpoint"
        write_bps = lldb.SBBreakpointList(self.orig_target)
        bkpt.AddName(good_bkpt_name)
        write_bps.Append(bkpt)

        error = lldb.SBError()
        error = self.orig_target.BreakpointsWriteToFile(self.bkpts_file_spec, write_bps)
        self.assertSuccess(error, "Failed writing breakpoints to file")

        copy_bps = lldb.SBBreakpointList(self.copy_target)
        names_list = lldb.SBStringList()
        names_list.AppendString("NoSuchName")

        error = self.copy_target.BreakpointsCreateFromFile(
            self.bkpts_file_spec, names_list, copy_bps
        )
        self.assertSuccess(error, "Failed reading breakpoints from file")
        self.assertEqual(
            copy_bps.GetSize(), 0, "Found breakpoints with a nonexistent name."
        )

        names_list.AppendString(good_bkpt_name)
        error = self.copy_target.BreakpointsCreateFromFile(
            self.bkpts_file_spec, names_list, copy_bps
        )
        self.assertSuccess(error, "Failed reading breakpoints from file")
        self.assertEqual(copy_bps.GetSize(), 1, "Found the matching breakpoint.")

    def do_check_extra_args(self):
        import side_effect

        interp = self.dbg.GetCommandInterpreter()
        error = lldb.SBError()

        script_name = os.path.join(self.getSourceDir(), "resolver.py")

        command = "command script import " + script_name
        result = lldb.SBCommandReturnObject()
        interp.HandleCommand(command, result)
        self.assertTrue(
            result.Succeeded(), "com scr imp failed: %s" % (result.GetError())
        )

        # First make sure a scripted breakpoint with no args works:
        bkpt = self.orig_target.BreakpointCreateFromScript(
            "resolver.Resolver",
            lldb.SBStructuredData(),
            lldb.SBFileSpecList(),
            lldb.SBFileSpecList(),
        )
        self.assertTrue(bkpt.IsValid(), "Bkpt is valid")
        write_bps = lldb.SBBreakpointList(self.orig_target)

        error = self.orig_target.BreakpointsWriteToFile(self.bkpts_file_spec, write_bps)
        self.assertSuccess(error, "Failed writing breakpoints")

        side_effect.g_extra_args = None
        copy_bps = lldb.SBBreakpointList(self.copy_target)
        error = self.copy_target.BreakpointsCreateFromFile(
            self.bkpts_file_spec, copy_bps
        )
        self.assertSuccess(error, "Failed reading breakpoints")

        self.assertEqual(copy_bps.GetSize(), 1, "Got one breakpoint from file.")
        no_keys = lldb.SBStringList()
        side_effect.g_extra_args.GetKeys(no_keys)
        self.assertEqual(no_keys.GetSize(), 0, "Should have no keys")

        self.orig_target.DeleteAllBreakpoints()
        self.copy_target.DeleteAllBreakpoints()

        # Now try one with extra args:

        extra_args = lldb.SBStructuredData()
        stream = lldb.SBStream()
        stream.Print('{"first_arg" : "first_value", "second_arg" : "second_value"}')
        extra_args.SetFromJSON(stream)
        self.assertTrue(extra_args.IsValid(), "SBStructuredData is valid.")

        bkpt = self.orig_target.BreakpointCreateFromScript(
            "resolver.Resolver",
            extra_args,
            lldb.SBFileSpecList(),
            lldb.SBFileSpecList(),
        )
        self.assertTrue(bkpt.IsValid(), "Bkpt is valid")
        write_bps = lldb.SBBreakpointList(self.orig_target)

        error = self.orig_target.BreakpointsWriteToFile(self.bkpts_file_spec, write_bps)
        self.assertSuccess(error, "Failed writing breakpoints")

        orig_extra_args = side_effect.g_extra_args
        self.assertTrue(orig_extra_args.IsValid(), "Extra args originally valid")

        orig_keys = lldb.SBStringList()
        orig_extra_args.GetKeys(orig_keys)
        self.assertEqual(2, orig_keys.GetSize(), "Should have two keys")

        side_effect.g_extra_args = None

        copy_bps = lldb.SBBreakpointList(self.copy_target)
        error = self.copy_target.BreakpointsCreateFromFile(
            self.bkpts_file_spec, copy_bps
        )
        self.assertSuccess(error, "Failed reading breakpoints")

        self.assertEqual(copy_bps.GetSize(), 1, "Got one breakpoint from file.")

        copy_extra_args = side_effect.g_extra_args
        copy_keys = lldb.SBStringList()
        copy_extra_args.GetKeys(copy_keys)
        self.assertEqual(2, copy_keys.GetSize(), "Copy should have two keys")

        for idx in range(0, orig_keys.GetSize()):
            key = orig_keys.GetStringAtIndex(idx)
            copy_value = copy_extra_args.GetValueForKey(key).GetStringValue(100)

            if key == "first_arg":
                self.assertEqual(copy_value, "first_value")
            elif key == "second_arg":
                self.assertEqual(copy_value, "second_value")
            else:
                self.Fail("Unknown key: %s" % (key))
