diff options
Diffstat (limited to 'lldb/test/API/commands')
28 files changed, 299 insertions, 38 deletions
diff --git a/lldb/test/API/commands/command/script/add/TestAddParsedCommand.py b/lldb/test/API/commands/command/script/add/TestAddParsedCommand.py index 6fac1eba919b..9deebe29eaae 100644 --- a/lldb/test/API/commands/command/script/add/TestAddParsedCommand.py +++ b/lldb/test/API/commands/command/script/add/TestAddParsedCommand.py @@ -34,6 +34,7 @@ class ParsedCommandTestCase(TestBase): else: (short_opt, type, long_opt) = elem substrs.append(f"-{short_opt} <{type}> ( --{long_opt} <{type}> )") + self.expect("help " + cmd_name, substrs=substrs) def run_one_repeat(self, commands, expected_num_errors): @@ -215,6 +216,19 @@ class ParsedCommandTestCase(TestBase): "bool-arg (set: True): False", "shlib-name (set: True): Something", "disk-file-name (set: False):", + "flag-value (set: False):", + "line-num (set: False):", + "enum-option (set: False):", + ], + ) + # Make sure flag values work: + self.expect( + "no-args -b false -s Something -f", + substrs=[ + "bool-arg (set: True): False", + "shlib-name (set: True): Something", + "disk-file-name (set: False):", + "flag-value (set: True):", "line-num (set: False):", "enum-option (set: False):", ], @@ -295,7 +309,7 @@ class ParsedCommandTestCase(TestBase): # no-args turns off auto-repeat results = self.run_one_repeat("no-args\n\n", 1) - self.assertIn("No auto repeat", results, "Got auto-repeat error") + self.assertIn("no auto repeat", results, "Got auto-repeat error") # one-args does the normal repeat results = self.run_one_repeat("one-arg-no-opt ONE_ARG\n\n", 0) diff --git a/lldb/test/API/commands/command/script/add/test_commands.py b/lldb/test/API/commands/command/script/add/test_commands.py index b15ea935c058..db302796819a 100644 --- a/lldb/test/API/commands/command/script/add/test_commands.py +++ b/lldb/test/API/commands/command/script/add/test_commands.py @@ -16,10 +16,16 @@ class ReportingCmd(ParsedCommand): if len(opt_def): result.AppendMessage("Options:\n") for long_option, elem in opt_def.items(): - dest = elem["dest"] - result.AppendMessage( - f"{long_option} (set: {elem['_value_set']}): {object.__getattribute__(self.get_parser(), dest)}\n" - ) + if "value_type" in elem: + print(f"Looking at {long_option} - {elem}") + dest = elem["dest"] + result.AppendMessage( + f"{long_option} (set: {elem['_value_set']}): {object.__getattribute__(self.get_parser(), dest)}\n" + ) + else: + result.AppendMessage( + f"{long_option} (set: {elem['_value_set']}): flag value\n" + ) else: result.AppendMessage("No options\n") @@ -78,6 +84,8 @@ class NoArgsCommand(ReportingCmd): default=None, ) + ov_parser.add_option("f", "flag-value", "This is a flag value") + ov_parser.add_option( "l", "line-num", diff --git a/lldb/test/API/commands/expression/import-std-module/array/TestArrayFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/array/TestArrayFromStdModule.py index a488276c2e54..ed028a1a4ea3 100644 --- a/lldb/test/API/commands/expression/import-std-module/array/TestArrayFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/array/TestArrayFromStdModule.py @@ -11,7 +11,6 @@ class TestCase(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/deque-basic/TestDequeFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/deque-basic/TestDequeFromStdModule.py index 38b8508b516d..0fb6e883597d 100644 --- a/lldb/test/API/commands/expression/import-std-module/deque-basic/TestDequeFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/deque-basic/TestDequeFromStdModule.py @@ -11,7 +11,6 @@ class TestBasicDeque(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/deque-dbg-info-content/TestDbgInfoContentDequeFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/deque-dbg-info-content/TestDbgInfoContentDequeFromStdModule.py index 85eaa8fe39ea..e631a8737637 100644 --- a/lldb/test/API/commands/expression/import-std-module/deque-dbg-info-content/TestDbgInfoContentDequeFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/deque-dbg-info-content/TestDbgInfoContentDequeFromStdModule.py @@ -12,7 +12,6 @@ class TestDbgInfoContentDeque(TestBase): @skipIf(compiler=no_match("clang")) @skipIf(compiler="clang", compiler_version=["<", "18.0"]) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/forward_list-dbg-info-content/TestDbgInfoContentForwardListFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/forward_list-dbg-info-content/TestDbgInfoContentForwardListFromStdModule.py index a3a409d678ee..1d0f9ccf18c6 100644 --- a/lldb/test/API/commands/expression/import-std-module/forward_list-dbg-info-content/TestDbgInfoContentForwardListFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/forward_list-dbg-info-content/TestDbgInfoContentForwardListFromStdModule.py @@ -11,7 +11,6 @@ class TestDbgInfoContentForwardList(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/forward_list/TestForwardListFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/forward_list/TestForwardListFromStdModule.py index c9f4a1588f39..a6ba0810e68e 100644 --- a/lldb/test/API/commands/expression/import-std-module/forward_list/TestForwardListFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/forward_list/TestForwardListFromStdModule.py @@ -11,7 +11,6 @@ class TestBasicForwardList(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/iterator/TestIteratorFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/iterator/TestIteratorFromStdModule.py index 5c82ac352abb..370c3674faec 100644 --- a/lldb/test/API/commands/expression/import-std-module/iterator/TestIteratorFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/iterator/TestIteratorFromStdModule.py @@ -11,7 +11,6 @@ class TestCase(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/list-dbg-info-content/TestDbgInfoContentListFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/list-dbg-info-content/TestDbgInfoContentListFromStdModule.py index 0ecc244412da..b26bd7dedda8 100644 --- a/lldb/test/API/commands/expression/import-std-module/list-dbg-info-content/TestDbgInfoContentListFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/list-dbg-info-content/TestDbgInfoContentListFromStdModule.py @@ -13,7 +13,6 @@ class TestDbgInfoContentList(TestBase): @skipIf(compiler=no_match("clang")) @skipIf(compiler="clang", compiler_version=["<", "12.0"]) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/list/TestListFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/list/TestListFromStdModule.py index f29f353ae079..6253a35e926d 100644 --- a/lldb/test/API/commands/expression/import-std-module/list/TestListFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/list/TestListFromStdModule.py @@ -11,7 +11,6 @@ class TestBasicList(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/non-module-type-separation/TestNonModuleTypeSeparation.py b/lldb/test/API/commands/expression/import-std-module/non-module-type-separation/TestNonModuleTypeSeparation.py index 5e0ab48cfa5c..cc91ddcc538b 100644 --- a/lldb/test/API/commands/expression/import-std-module/non-module-type-separation/TestNonModuleTypeSeparation.py +++ b/lldb/test/API/commands/expression/import-std-module/non-module-type-separation/TestNonModuleTypeSeparation.py @@ -12,7 +12,6 @@ class TestCase(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): """ This test is creating ValueObjects with both C++ module and debug diff --git a/lldb/test/API/commands/expression/import-std-module/shared_ptr-dbg-info-content/TestSharedPtrDbgInfoContentFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/shared_ptr-dbg-info-content/TestSharedPtrDbgInfoContentFromStdModule.py index 50419b6f761c..5bfdb9baf663 100644 --- a/lldb/test/API/commands/expression/import-std-module/shared_ptr-dbg-info-content/TestSharedPtrDbgInfoContentFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/shared_ptr-dbg-info-content/TestSharedPtrDbgInfoContentFromStdModule.py @@ -11,7 +11,6 @@ class TestSharedPtrDbgInfoContent(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/shared_ptr/TestSharedPtrFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/shared_ptr/TestSharedPtrFromStdModule.py index 9f04361c48d7..da86466018bb 100644 --- a/lldb/test/API/commands/expression/import-std-module/shared_ptr/TestSharedPtrFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/shared_ptr/TestSharedPtrFromStdModule.py @@ -10,9 +10,8 @@ from lldbsuite.test import lldbutil class TestSharedPtr(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) - @skipIf(compiler="clang", compiler_version=["<", "17.0"]) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin + @skipIf(compiler="clang", compiler_version=["<", "17.0"]) def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/vector-dbg-info-content/TestDbgInfoContentVectorFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/vector-dbg-info-content/TestDbgInfoContentVectorFromStdModule.py index ba4df40bbbc5..1c32222e64f1 100644 --- a/lldb/test/API/commands/expression/import-std-module/vector-dbg-info-content/TestDbgInfoContentVectorFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/vector-dbg-info-content/TestDbgInfoContentVectorFromStdModule.py @@ -14,7 +14,6 @@ class TestDbgInfoContentVector(TestBase): @skipIf(compiler="clang", compiler_version=["<", "12.0"]) @skipIf(macos_version=["<", "14.0"]) @skipIfDarwin # https://github.com/llvm/llvm-project/issues/106475 - @skipIfLinux def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/vector-of-vectors/TestVectorOfVectorsFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/vector-of-vectors/TestVectorOfVectorsFromStdModule.py index 6fa9dd5b6f56..2cddce09aa8b 100644 --- a/lldb/test/API/commands/expression/import-std-module/vector-of-vectors/TestVectorOfVectorsFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/vector-of-vectors/TestVectorOfVectorsFromStdModule.py @@ -11,7 +11,6 @@ class TestVectorOfVectors(TestBase): @add_test_categories(["libc++"]) @skipIf(compiler=no_match("clang")) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/weak_ptr-dbg-info-content/TestDbgInfoContentWeakPtrFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/weak_ptr-dbg-info-content/TestDbgInfoContentWeakPtrFromStdModule.py index 19d24c1bcb89..28edf1999362 100644 --- a/lldb/test/API/commands/expression/import-std-module/weak_ptr-dbg-info-content/TestDbgInfoContentWeakPtrFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/weak_ptr-dbg-info-content/TestDbgInfoContentWeakPtrFromStdModule.py @@ -12,7 +12,6 @@ class TestDbgInfoContentWeakPtr(TestBase): @skipIf(compiler=no_match("clang")) @skipIf(compiler="clang", compiler_version=["<", "17.0"]) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/expression/import-std-module/weak_ptr/TestWeakPtrFromStdModule.py b/lldb/test/API/commands/expression/import-std-module/weak_ptr/TestWeakPtrFromStdModule.py index e3cc9b92569c..f0a0a46a73e9 100644 --- a/lldb/test/API/commands/expression/import-std-module/weak_ptr/TestWeakPtrFromStdModule.py +++ b/lldb/test/API/commands/expression/import-std-module/weak_ptr/TestWeakPtrFromStdModule.py @@ -12,7 +12,6 @@ class TestSharedPtr(TestBase): @skipIf(compiler=no_match("clang")) @skipIf(compiler="clang", compiler_version=["<", "17.0"]) @skipIf(macos_version=["<", "15.0"]) - @skipUnlessDarwin def test(self): self.build() diff --git a/lldb/test/API/commands/frame/select/TestFrameSelect.py b/lldb/test/API/commands/frame/select/TestFrameSelect.py index cb10105c0fe7..9e21495d4b53 100644 --- a/lldb/test/API/commands/frame/select/TestFrameSelect.py +++ b/lldb/test/API/commands/frame/select/TestFrameSelect.py @@ -23,12 +23,12 @@ class TestFrameSelect(TestBase): self.expect( "frame select -r -1", error=True, - substrs=["Already at the bottom of the stack."], + substrs=["already at the bottom of the stack"], ) self.expect( "frame select -r -2147483647", error=True, - substrs=["Already at the bottom of the stack."], + substrs=["already at the bottom of the stack"], ) self.expect( "frame select -r -2147483648", @@ -61,7 +61,7 @@ class TestFrameSelect(TestBase): self.expect( "frame select -r 1", error=True, - substrs=["Already at the top of the stack."], + substrs=["already at the top of the stack"], ) @no_debug_info_test diff --git a/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/TestFrameVarDILArraySubscript.py b/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/TestFrameVarDILArraySubscript.py index 0f5605718939..f47e86266f47 100644 --- a/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/TestFrameVarDILArraySubscript.py +++ b/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/TestFrameVarDILArraySubscript.py @@ -66,30 +66,27 @@ class TestFrameVarDILArraySubscript(TestBase): self.expect( "frame var 'int_arr[1.0]'", error=True, - substrs=["expected 'r_square', got: <'.'"], + substrs=["failed to parse integer constant: <'1.0' (float_constant)>"], ) - # Base should be a "pointer to T" and index should be of an integral type. - self.expect( - "frame var 'idx_1[0]'", - error=True, - substrs=["subscripted value is not an array or pointer"], - ) + # Test accessing bits in scalar types. + self.expect_var_path("idx_1[0]", value="1") + self.expect_var_path("idx_1[1]", value="0") + self.expect_var_path("1[0]", value="1") + + # Bit access not valid for a reference. self.expect( "frame var 'idx_1_ref[0]'", error=True, - substrs=["subscripted value is not an array or pointer"], + substrs=["bitfield range 0-0 is not valid"], ) + + # Base should be a "pointer to T" and index should be of an integral type. self.expect( "frame var 'int_arr[int_ptr]'", error=True, substrs=["failed to parse integer constant"], ) - self.expect( - "frame var '1[2]'", - error=True, - substrs=["Unexpected token"], - ) # Base should not be a pointer to void self.expect( @@ -105,6 +102,8 @@ class TestFrameVarDILArraySubscript(TestBase): ) self.runCmd("settings set target.experimental.use-DIL true") + self.runCmd("script from myArraySynthProvider import *") + self.runCmd("type synth add -l myArraySynthProvider myArray") # Test synthetic value subscription self.expect_var_path("vector[1]", value="2") @@ -113,3 +112,7 @@ class TestFrameVarDILArraySubscript(TestBase): error=True, substrs=["array index 100 is not valid"], ) + self.expect( + "frame var 'ma_ptr[0]'", + substrs=["(myArray) ma_ptr[0] = ([0] = 7, [1] = 8, [2] = 9, [3] = 10)"], + ) diff --git a/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/main.cpp b/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/main.cpp index a9a3612dfae5..03ad3e872ca7 100644 --- a/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/main.cpp +++ b/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/main.cpp @@ -1,5 +1,11 @@ #include <vector> +class myArray { +public: + int m_array[4] = {7, 8, 9, 10}; + int m_arr_size = 4; +}; + int main(int argc, char **argv) { int int_arr[] = {1, 2, 3}; int *int_ptr = int_arr; @@ -29,5 +35,8 @@ int main(int argc, char **argv) { std::vector<int> vector = {1, 2, 3}; + myArray ma; + myArray *ma_ptr = &ma; + return 0; // Set a breakpoint here } diff --git a/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/myArraySynthProvider.py b/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/myArraySynthProvider.py new file mode 100644 index 000000000000..167899bd3907 --- /dev/null +++ b/lldb/test/API/commands/frame/var-dil/basics/ArraySubscript/myArraySynthProvider.py @@ -0,0 +1,33 @@ +import lldb + + +class myArraySynthProvider: + def __init__(self, valobj, dict): + self.valobj = valobj + + def num_children(self): + size_valobj = self.valobj.GetChildMemberWithName("m_arr_size") + if size_valobj: + return size_valobj.GetValueAsUnsigned(0) + return 0 + + def get_child_at_index(self, index): + size_valobj = self.valobj.GetChildMemberWithName("m_arr_size") + arr = self.valobj.GetChildMemberWithName("m_array") + if not size_valobj or not arr: + return None + max_idx = size_valobj.GetValueAsUnsigned(0) + if index >= max_idx: + return None + return arr.GetChildAtIndex(index) + + def get_child_index(self, name): + if name == "[0]": + return 0 + if name == "[1]": + return + if name == "[2]": + return 2 + if name == "[3]": + return 3 + return -1 diff --git a/lldb/test/API/commands/frame/var-dil/basics/Indirection/TestFrameVarDILIndirection.py b/lldb/test/API/commands/frame/var-dil/basics/Indirection/TestFrameVarDILIndirection.py index 38c72131d797..28eba4f1a70b 100644 --- a/lldb/test/API/commands/frame/var-dil/basics/Indirection/TestFrameVarDILIndirection.py +++ b/lldb/test/API/commands/frame/var-dil/basics/Indirection/TestFrameVarDILIndirection.py @@ -35,7 +35,7 @@ class TestFrameVarDILIndirection(TestBase): self.expect( "frame variable '*1'", error=True, - substrs=["Unexpected token: <'1' (numeric_constant)>"], + substrs=["dereference failed: not a pointer, reference or array type"], ) self.expect( "frame variable '*val'", diff --git a/lldb/test/API/commands/frame/var-dil/expr/Literals/Makefile b/lldb/test/API/commands/frame/var-dil/expr/Literals/Makefile new file mode 100644 index 000000000000..99998b20bcb0 --- /dev/null +++ b/lldb/test/API/commands/frame/var-dil/expr/Literals/Makefile @@ -0,0 +1,3 @@ +CXX_SOURCES := main.cpp + +include Makefile.rules diff --git a/lldb/test/API/commands/frame/var-dil/expr/Literals/TestFrameVarDILLiterals.py b/lldb/test/API/commands/frame/var-dil/expr/Literals/TestFrameVarDILLiterals.py new file mode 100644 index 000000000000..431ec2829bc7 --- /dev/null +++ b/lldb/test/API/commands/frame/var-dil/expr/Literals/TestFrameVarDILLiterals.py @@ -0,0 +1,88 @@ +""" +Test DIL literals. +""" + +import lldb +from lldbsuite.test.lldbtest import * +from lldbsuite.test.decorators import * +from lldbsuite.test import lldbutil + + +class TestFrameVarDILLiterals(TestBase): + NO_DEBUG_INFO_TESTCASE = True + + def test_literals(self): + self.build() + (target, process, thread, bkpt) = lldbutil.run_to_source_breakpoint( + self, "Set a breakpoint here", lldb.SBFileSpec("main.cpp") + ) + + self.runCmd("settings set target.experimental.use-DIL true") + + # Check number literals parsing + self.expect_var_path("1.0", value="1", type="double") + self.expect_var_path("1.0f", value="1", type="float") + self.expect_var_path("0x1.2p+3f", value="9", type="float") + self.expect_var_path("1", value="1", type="int") + self.expect_var_path("1u", value="1", type="unsigned int") + self.expect_var_path("0b1l", value="1", type="long") + self.expect_var_path("01ul", value="1", type="unsigned long") + self.expect_var_path("01lu", value="1", type="unsigned long") + self.expect_var_path("0o1ll", value="1", type="long long") + self.expect_var_path("0x1ULL", value="1", type="unsigned long long") + self.expect_var_path("0x1llu", value="1", type="unsigned long long") + self.expect( + "frame var '1LLL'", + error=True, + substrs=["Failed to parse token as numeric-constant"], + ) + self.expect( + "frame var '1ullu'", + error=True, + substrs=["Failed to parse token as numeric-constant"], + ) + + # Check integer literal type edge cases (dil::Interpreter::PickIntegerType) + frame = thread.GetFrameAtIndex(0) + v = frame.GetValueForVariablePath("argc") + # Creating an SBType from a BasicType still requires any value from the frame + int_size = v.GetType().GetBasicType(lldb.eBasicTypeInt).GetByteSize() + long_size = v.GetType().GetBasicType(lldb.eBasicTypeLong).GetByteSize() + longlong_size = v.GetType().GetBasicType(lldb.eBasicTypeLongLong).GetByteSize() + + longlong_str = "0x" + "F" * longlong_size * 2 + longlong_str = str(int(longlong_str, 16)) + self.assert_literal_type(frame, longlong_str, lldb.eBasicTypeUnsignedLongLong) + toolong_str = "0x" + "F" * longlong_size * 2 + "F" + self.expect( + f"frame var '{toolong_str}'", + error=True, + substrs=[ + "integer literal is too large to be represented in any integer type" + ], + ) + + # These check only apply if adjacent types have different sizes + if int_size < long_size: + # For exmaple, 0xFFFFFFFF and 4294967295 will have different types + # even though the numeric value is the same + hex_str = "0x" + "F" * int_size * 2 + dec_str = str(int(hex_str, 16)) + self.assert_literal_type(frame, hex_str, lldb.eBasicTypeUnsignedInt) + self.assert_literal_type(frame, dec_str, lldb.eBasicTypeLong) + long_str = "0x" + "F" * int_size * 2 + "F" + ulong_str = long_str + "u" + self.assert_literal_type(frame, long_str, lldb.eBasicTypeLong) + self.assert_literal_type(frame, ulong_str, lldb.eBasicTypeUnsignedLong) + if long_size < longlong_size: + longlong_str = "0x" + "F" * long_size * 2 + "F" + ulonglong_str = longlong_str + "u" + self.assert_literal_type(frame, longlong_str, lldb.eBasicTypeLongLong) + self.assert_literal_type( + frame, ulonglong_str, lldb.eBasicTypeUnsignedLongLong + ) + + def assert_literal_type(self, frame, literal, expected_type): + value = frame.GetValueForVariablePath(literal) + basic_type = value.GetType().GetBasicType() + self.assertEqual(basic_type, expected_type) diff --git a/lldb/test/API/commands/frame/var-dil/expr/Literals/main.cpp b/lldb/test/API/commands/frame/var-dil/expr/Literals/main.cpp new file mode 100644 index 000000000000..c9bd8afb0d71 --- /dev/null +++ b/lldb/test/API/commands/frame/var-dil/expr/Literals/main.cpp @@ -0,0 +1,3 @@ +int main(int argc, char **argv) { + return 0; // Set a breakpoint here +} diff --git a/lldb/test/API/commands/statistics/basic/TestStats.py b/lldb/test/API/commands/statistics/basic/TestStats.py index e9ee8b8661e5..c8527abf3c84 100644 --- a/lldb/test/API/commands/statistics/basic/TestStats.py +++ b/lldb/test/API/commands/statistics/basic/TestStats.py @@ -1,6 +1,7 @@ import json import os import re +import shutil import lldb from lldbsuite.test.decorators import * @@ -179,6 +180,7 @@ class TestCase(TestBase): "totalDebugInfoParseTime", "totalDwoFileCount", "totalLoadedDwoFileCount", + "totalDwoErrorCount", ] self.verify_keys(debug_stats, '"debug_stats"', debug_stat_keys, None) if self.getPlatform() != "windows": @@ -291,6 +293,7 @@ class TestCase(TestBase): "totalDebugInfoParseTime", "totalDwoFileCount", "totalLoadedDwoFileCount", + "totalDwoErrorCount", ] self.verify_keys(debug_stats, '"debug_stats"', debug_stat_keys, None) stats = debug_stats["targets"][0] @@ -331,6 +334,7 @@ class TestCase(TestBase): "totalDebugInfoByteSize", "totalDwoFileCount", "totalLoadedDwoFileCount", + "totalDwoErrorCount", ] self.verify_keys(debug_stats, '"debug_stats"', debug_stat_keys, None) @@ -385,6 +389,7 @@ class TestCase(TestBase): "totalDebugInfoByteSize", "totalDwoFileCount", "totalLoadedDwoFileCount", + "totalDwoErrorCount", ] self.verify_keys(debug_stats, '"debug_stats"', debug_stat_keys, None) stats = debug_stats["targets"][0] @@ -407,6 +412,7 @@ class TestCase(TestBase): "symbolTableSavedToCache", "dwoFileCount", "loadedDwoFileCount", + "dwoErrorCount", "triple", "uuid", ] @@ -497,6 +503,7 @@ class TestCase(TestBase): "totalDebugInfoByteSize", "totalDwoFileCount", "totalLoadedDwoFileCount", + "totalDwoErrorCount", ] self.verify_keys(debug_stats, '"debug_stats"', debug_stat_keys, None) target_stats = debug_stats["targets"][0] @@ -655,6 +662,99 @@ class TestCase(TestBase): self.assertEqual(debug_stats["totalDwoFileCount"], 2) self.assertEqual(debug_stats["totalLoadedDwoFileCount"], 2) + @add_test_categories(["dwo"]) + def test_dwo_missing_error_stats(self): + """ + Test that DWO missing errors are reported correctly in statistics. + This test: + 1) Builds a program with split DWARF (.dwo files) + 2) Delete one of the two .dwo files + 3) Verify that 1 DWO error is reported in statistics + """ + da = { + "CXX_SOURCES": "dwo_error_main.cpp dwo_error_foo.cpp", + "EXE": self.getBuildArtifact("a.out"), + } + # -gsplit-dwarf creates separate .dwo files, + # Expected output: dwo_error_main.dwo (contains main) and dwo_error_foo.dwo (contains foo struct/function) + self.build(dictionary=da, debug_info="dwo") + exe = self.getBuildArtifact("a.out") + + expected_dwo_files = [ + self.getBuildArtifact("dwo_error_main.dwo"), + self.getBuildArtifact("dwo_error_foo.dwo"), + ] + + # Verify expected files exist + for dwo_file in expected_dwo_files: + self.assertTrue( + os.path.exists(dwo_file), + f"Expected .dwo file does not exist: {dwo_file}", + ) + + # Remove one of .dwo files to trigger DWO load error + dwo_main_file = self.getBuildArtifact("dwo_error_main.dwo") + os.remove(dwo_main_file) + + target = self.createTestTarget(file_path=exe) + debug_stats = self.get_stats() + + # Check DWO load error statistics are reported + self.assertIn("totalDwoErrorCount", debug_stats) + self.assertEqual(debug_stats["totalDwoErrorCount"], 1) + + # Since there's only one module, module stats should have the same count as total count + self.assertIn("dwoErrorCount", debug_stats["modules"][0]) + self.assertEqual(debug_stats["modules"][0]["dwoErrorCount"], 1) + + @add_test_categories(["dwo"]) + def test_dwo_id_mismatch_error_stats(self): + """ + Test that DWO ID mismatch errors are reported correctly in statistics. + This test: + 1) Builds a program with split DWARF (.dwo files) + 2) Replace one of the .dwo files with a mismatched one to cause a DWO ID mismatch error + 3) Verifies that a DWO error is reported in statistics + """ + da = { + "CXX_SOURCES": "dwo_error_main.cpp dwo_error_foo.cpp", + "EXE": self.getBuildArtifact("a.out"), + } + # -gsplit-dwarf creates separate .dwo files, + # Expected output: dwo_error_main.dwo (contains main) and dwo_error_foo.dwo (contains foo struct/function) + self.build(dictionary=da, debug_info="dwo") + exe = self.getBuildArtifact("a.out") + + expected_dwo_files = [ + self.getBuildArtifact("dwo_error_main.dwo"), + self.getBuildArtifact("dwo_error_foo.dwo"), + ] + + # Verify expected files exist + for dwo_file in expected_dwo_files: + self.assertTrue( + os.path.exists(dwo_file), + f"Expected .dwo file does not exist: {dwo_file}", + ) + + # Replace one of the original .dwo file content with another one to trigger DWO ID mismatch error + dwo_foo_file = self.getBuildArtifact("dwo_error_foo.dwo") + dwo_main_file = self.getBuildArtifact("dwo_error_main.dwo") + + shutil.copy(dwo_main_file, dwo_foo_file) + + # Create a new target and get stats + target = self.createTestTarget(file_path=exe) + debug_stats = self.get_stats() + + # Check that DWO load error statistics are reported + self.assertIn("totalDwoErrorCount", debug_stats) + self.assertEqual(debug_stats["totalDwoErrorCount"], 1) + + # Since there's only one module, module stats should have the same count as total count + self.assertIn("dwoErrorCount", debug_stats["modules"][0]) + self.assertEqual(debug_stats["modules"][0]["dwoErrorCount"], 1) + @skipUnlessDarwin @no_debug_info_test def test_dsym_binary_has_symfile_in_stats(self): diff --git a/lldb/test/API/commands/statistics/basic/dwo_error_foo.cpp b/lldb/test/API/commands/statistics/basic/dwo_error_foo.cpp new file mode 100644 index 000000000000..41618bdcee95 --- /dev/null +++ b/lldb/test/API/commands/statistics/basic/dwo_error_foo.cpp @@ -0,0 +1,10 @@ +struct foo { + int x; + bool y; +}; + +void dwo_error_foo() { + foo f; + f.x = 1; + f.y = true; +} diff --git a/lldb/test/API/commands/statistics/basic/dwo_error_main.cpp b/lldb/test/API/commands/statistics/basic/dwo_error_main.cpp new file mode 100644 index 000000000000..4f09bd74e1fd --- /dev/null +++ b/lldb/test/API/commands/statistics/basic/dwo_error_main.cpp @@ -0,0 +1,5 @@ +void dwo_error_foo(); +int main() { + dwo_error_foo(); + return 0; +} |
