[Lldb-commits] [lldb] [lldb] Add support for updating string during debug process (PR #67782)
kpdev wrote: @jimingham Please take a look: https://github.com/llvm/llvm-project/pull/67782#issuecomment-2047369473 https://github.com/llvm/llvm-project/pull/67782 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][Windows] Fixed LibcxxChronoTimePointSecondsSummaryProvider() (PR #92701)
https://github.com/labath approved this pull request. https://github.com/llvm/llvm-project/pull/92701 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Don't send expanded descriptions for "hover" expressions (PR #92726)
https://github.com/labath created https://github.com/llvm/llvm-project/pull/92726 VSCode will automatically ask for the children (in structured form) so there's no point in sending the textual representation. This can make displaying hover popups for complex variables with complicated data formatters much faster. See discussion on #77026 for context. >From 9d126afa09c7c2f73852da3ba943e1a74498cba4 Mon Sep 17 00:00:00 2001 From: Pavel Labath Date: Mon, 20 May 2024 08:18:07 + Subject: [PATCH] [lldb-dap] Don't send expanded descriptions for "hover" expressions VSCode will automatically ask for the children (in structured form) so there's no point in sending the textual representation. This can make displaying hover popups for complex variables with complicated data formatters much faster. See discussion on #77026 for context. --- .../lldb-dap/evaluate/TestDAP_evaluate.py | 2 +- .../lldb-dap/variables/TestDAP_variables.py | 29 --- lldb/tools/lldb-dap/JSONUtils.cpp | 6 ++-- 3 files changed, 10 insertions(+), 27 deletions(-) diff --git a/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py b/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py index 57cabf5b7f411..68c57ad775544 100644 --- a/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py +++ b/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py @@ -27,7 +27,7 @@ def assertEvaluateFailure(self, expression): ) def isResultExpandedDescription(self): -return self.context == "repl" or self.context == "hover" +return self.context == "repl" def isExpressionParsedExpected(self): return self.context != "hover" diff --git a/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py b/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py index 07ab6d5a63eb6..57c17e5ea9d3d 100644 --- a/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py +++ b/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py @@ -502,29 +502,12 @@ def do_test_scopes_and_evaluate_expansion(self, enableAutoVariableSummaries: boo }, "hover": { "equals": {"type": "PointType"}, -"equals": { -"result": """(PointType) pt = { - x = 11 - y = 22 - buffer = { -[0] = 0 -[1] = 1 -[2] = 2 -[3] = 3 -[4] = 4 -[5] = 5 -[6] = 6 -[7] = 7 -[8] = 8 -[9] = 9 -[10] = 10 -[11] = 11 -[12] = 12 -[13] = 13 -[14] = 14 -[15] = 15 - } -}""" +"startswith": { +"result": ( +"{x:11, y:22, buffer:{...}}" +if enableAutoVariableSummaries +else "PointType @ 0x" +) }, "missing": ["indexedVariables"], "hasVariablesReference": True, diff --git a/lldb/tools/lldb-dap/JSONUtils.cpp b/lldb/tools/lldb-dap/JSONUtils.cpp index bec277332bcf0..069877dbab339 100644 --- a/lldb/tools/lldb-dap/JSONUtils.cpp +++ b/lldb/tools/lldb-dap/JSONUtils.cpp @@ -1065,9 +1065,9 @@ llvm::json::Object VariableDescription::GetVariableExtensionsJSON() { } std::string VariableDescription::GetResult(llvm::StringRef context) { - // In repl and hover context, the results can be displayed as multiple lines - // so more detailed descriptions can be returned. - if (context != "repl" && context != "hover") + // In repl context, the results can be displayed as multiple lines so more + // detailed descriptions can be returned. + if (context != "repl") return display_value; if (!v.IsValid()) ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Don't send expanded descriptions for "hover" expressions (PR #92726)
llvmbot wrote: @llvm/pr-subscribers-lldb Author: Pavel Labath (labath) Changes VSCode will automatically ask for the children (in structured form) so there's no point in sending the textual representation. This can make displaying hover popups for complex variables with complicated data formatters much faster. See discussion on #77026 for context. --- Full diff: https://github.com/llvm/llvm-project/pull/92726.diff 3 Files Affected: - (modified) lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py (+1-1) - (modified) lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py (+6-23) - (modified) lldb/tools/lldb-dap/JSONUtils.cpp (+3-3) ``diff diff --git a/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py b/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py index 57cabf5b7f411..68c57ad775544 100644 --- a/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py +++ b/lldb/test/API/tools/lldb-dap/evaluate/TestDAP_evaluate.py @@ -27,7 +27,7 @@ def assertEvaluateFailure(self, expression): ) def isResultExpandedDescription(self): -return self.context == "repl" or self.context == "hover" +return self.context == "repl" def isExpressionParsedExpected(self): return self.context != "hover" diff --git a/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py b/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py index 07ab6d5a63eb6..57c17e5ea9d3d 100644 --- a/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py +++ b/lldb/test/API/tools/lldb-dap/variables/TestDAP_variables.py @@ -502,29 +502,12 @@ def do_test_scopes_and_evaluate_expansion(self, enableAutoVariableSummaries: boo }, "hover": { "equals": {"type": "PointType"}, -"equals": { -"result": """(PointType) pt = { - x = 11 - y = 22 - buffer = { -[0] = 0 -[1] = 1 -[2] = 2 -[3] = 3 -[4] = 4 -[5] = 5 -[6] = 6 -[7] = 7 -[8] = 8 -[9] = 9 -[10] = 10 -[11] = 11 -[12] = 12 -[13] = 13 -[14] = 14 -[15] = 15 - } -}""" +"startswith": { +"result": ( +"{x:11, y:22, buffer:{...}}" +if enableAutoVariableSummaries +else "PointType @ 0x" +) }, "missing": ["indexedVariables"], "hasVariablesReference": True, diff --git a/lldb/tools/lldb-dap/JSONUtils.cpp b/lldb/tools/lldb-dap/JSONUtils.cpp index bec277332bcf0..069877dbab339 100644 --- a/lldb/tools/lldb-dap/JSONUtils.cpp +++ b/lldb/tools/lldb-dap/JSONUtils.cpp @@ -1065,9 +1065,9 @@ llvm::json::Object VariableDescription::GetVariableExtensionsJSON() { } std::string VariableDescription::GetResult(llvm::StringRef context) { - // In repl and hover context, the results can be displayed as multiple lines - // so more detailed descriptions can be returned. - if (context != "repl" && context != "hover") + // In repl context, the results can be displayed as multiple lines so more + // detailed descriptions can be returned. + if (context != "repl") return display_value; if (!v.IsValid()) `` https://github.com/llvm/llvm-project/pull/92726 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] 2217d17 - [lldb][Windows] Fixed LibcxxChronoTimePointSecondsSummaryProvider() (#92701)
Author: Dmitry Vasilyev Date: 2024-05-20T13:44:52+04:00 New Revision: 2217d1706a76d3f298899f824354ca9d96c45813 URL: https://github.com/llvm/llvm-project/commit/2217d1706a76d3f298899f824354ca9d96c45813 DIFF: https://github.com/llvm/llvm-project/commit/2217d1706a76d3f298899f824354ca9d96c45813.diff LOG: [lldb][Windows] Fixed LibcxxChronoTimePointSecondsSummaryProvider() (#92701) This patch fixes #92574. It is a replacement for #92575. Added: Modified: lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp lldb/test/API/functionalities/data-formatter/data-formatter-stl/libcxx/chrono/TestDataFormatterLibcxxChrono.py Removed: diff --git a/lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp b/lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp index e160fd0763939..b0e6fb7d6f5af 100644 --- a/lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp +++ b/lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp @@ -1098,6 +1098,7 @@ LibcxxChronoTimePointSecondsSummaryProvider(ValueObject &valobj, Stream &stream, if (!ptr_sp) return false; +#ifndef _WIN32 // The date time in the chrono library is valid in the range // [-32767-01-01T00:00:00Z, 32767-12-31T23:59:59Z]. A 64-bit time_t has a // larger range, the function strftime is not able to format the entire range @@ -1107,6 +1108,11 @@ LibcxxChronoTimePointSecondsSummaryProvider(ValueObject &valobj, Stream &stream, -1'096'193'779'200; // -32767-01-01T00:00:00Z const std::time_t chrono_timestamp_max = 971'890'963'199; // 32767-12-31T23:59:59Z +#else + const std::time_t chrono_timestamp_min = -43'200; // 1969-12-31T12:00:00Z + const std::time_t chrono_timestamp_max = + 32'536'850'399; // 3001-01-19T21:59:59 +#endif const std::time_t seconds = ptr_sp->GetValueAsSigned(0); if (seconds < chrono_timestamp_min || seconds > chrono_timestamp_max) @@ -1148,12 +1154,17 @@ LibcxxChronoTimepointDaysSummaryProvider(ValueObject &valobj, Stream &stream, if (!ptr_sp) return false; +#ifndef _WIN32 // The date time in the chrono library is valid in the range // [-32767-01-01Z, 32767-12-31Z]. A 32-bit time_t has a larger range, the // function strftime is not able to format the entire range of time_t. The // exact point has not been investigated; it's limited to chrono's range. const int chrono_timestamp_min = -12'687'428; // -32767-01-01Z const int chrono_timestamp_max = 11'248'737; // 32767-12-31Z +#else + const int chrono_timestamp_min = 0; // 1970-01-01Z + const int chrono_timestamp_max = 376'583; // 3001-01-19Z +#endif const int days = ptr_sp->GetValueAsSigned(0); if (days < chrono_timestamp_min || days > chrono_timestamp_max) diff --git a/lldb/test/API/functionalities/data-formatter/data-formatter-stl/libcxx/chrono/TestDataFormatterLibcxxChrono.py b/lldb/test/API/functionalities/data-formatter/data-formatter-stl/libcxx/chrono/TestDataFormatterLibcxxChrono.py index fb35481d55514..0737a5bc7e6eb 100644 --- a/lldb/test/API/functionalities/data-formatter/data-formatter-stl/libcxx/chrono/TestDataFormatterLibcxxChrono.py +++ b/lldb/test/API/functionalities/data-formatter/data-formatter-stl/libcxx/chrono/TestDataFormatterLibcxxChrono.py @@ -14,6 +14,7 @@ class LibcxxChronoDataFormatterTestCase(TestBase): @skipIf(compiler="clang", compiler_version=["<", "17.0"]) def test_with_run_command(self): """Test that that file and class static variables display correctly.""" +isNotWindowsHost = lldbplatformutil.getHostPlatform() != "windows" self.build() (self.target, process, thread, bkpt) = lldbutil.run_to_source_breakpoint( self, "break here", lldb.SBFileSpec("main.cpp", False) @@ -57,7 +58,11 @@ def test_with_run_command(self): self.expect( "frame variable ss_neg_date_time", substrs=[ -"ss_neg_date_time = date/time=-32767-01-01T00:00:00Z timestamp=-1096193779200 s" +( +"ss_neg_date_time = date/time=-32767-01-01T00:00:00Z timestamp=-1096193779200 s" +if isNotWindowsHost +else "ss_neg_date_time = timestamp=-1096193779200 s" +) ], ) self.expect( @@ -68,7 +73,11 @@ def test_with_run_command(self): self.expect( "frame variable ss_pos_date_time", substrs=[ -"ss_pos_date_time = date/time=32767-12-31T23:59:59Z timestamp=971890963199 s" +( +"ss_pos_date_time = date/time=32767-12-31T23:59:59Z timestamp=971890963199 s" +if isNotWindowsHost +else "ss_pos_date_time = timestamp=971890963199 s" +) ], ) self.expect( @@ -103,7 +112,13 @@ def test_with_run_command(self): ) self.expect(
[Lldb-commits] [lldb] [lldb][Windows] Fixed LibcxxChronoTimePointSecondsSummaryProvider() (PR #92701)
https://github.com/slydiman closed https://github.com/llvm/llvm-project/pull/92701 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][Windows] Skip the TestDataFormatterLibcxxChrono test to avoid python crash (PR #92575)
https://github.com/slydiman closed https://github.com/llvm/llvm-project/pull/92575 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Reapply [lldb][DWARF] Delay struct/class/union definition DIE searching when parsing declaration DIEs. (PR #92328)
@@ -2306,6 +2345,11 @@ bool DWARFASTParserClang::CompleteTypeFromDWARF(const DWARFDIE &die, if (!die) return false; + ParsedDWARFTypeAttributes attrs(die); labath wrote: > > How exactly do we get here in that case? > > From [#90663 > (comment)](https://github.com/llvm/llvm-project/pull/90663#issuecomment-2105194128), > .debug_names somehow contains entries that are declarations. This causes > `SymbolFileDWARF::FindDefinitionTypeForDWARFDeclContext` to return a type > created from declaration when searching for definition. I've re-read that. The debug names situation is troubling, but the thing I don't understand now why is this even specific to debug_names. After this patch, it should be fairly easy to trigger a situation where we're asked to complete a type, and we don't have the definition of that type. Why don't those cases lead to a crash? For example, what would happen if the name was simply not in the index? If I ignored this entire discussion, I would say that this check makes perfect sense: since we're delaying the search for the definition, it can happen that the we don't have the definition die at the point when we're asked to complete the type. So it seems perfectly reasonable to have this check _somewhere_. I just want to check whether this is the right place. > > A simple idea I have in mind is to make the > `GetForwardDeclCompilerTypeToDIE`'s value type to a pair `{DIERef, bool}`, > and the bool indicate if this is a definition or not. So we know that info > without extra attribute parsing. How do you think? Given that this extra bool is going to cause us to use eight more bytes per type, this doesn't necessarily seem like. This would use more memory, the previous implementation would use more time. Hard to say which one is better without some very precise measurements. Choosing blindly, I would stick with the current implementation, as it's easier to optimize the cpu time than it is to reclaim that memory (the real problem here is that `ParsedDWARFTypeAttributes` was optimized for the use case where one is going to use most of the attributes it has parsed (which is what happens in ParseTypeFromDWARF). Using it to essentially just check for the presence of DW_AT_declaration is wasteful, and you could write a much faster implementation if you were writing it for this use case specifically (but it's also not clear whether it's worthwhile to have a brand new implementation for this use case). https://github.com/llvm/llvm-project/pull/92328 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [WIP] [lldb][Progress] Report progress when completing types from DWARF (PR #91452)
labath wrote: > I attached to clang and printed an expression. That resulted in 16801 calls > to `Progress::Increment`, all of which I'm guessing translate to event > broadcasts. I collected some timing numbers: Thanks for doing this. What do these numbers include? Is it just the operation it self, or everything leading up to it as well. For example, is "expr var" just the timing of the "expr" command, or attach command as well. If the latter, then what's the baseline? https://github.com/llvm/llvm-project/pull/91452 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
https://github.com/labath created https://github.com/llvm/llvm-project/pull/92745 DWARFDebugInfo only knows how to resolve references in its own file, but in split dwarf, the index entries will refer to DIEs in the separate (DWO) file. To resolve the DIERef correctly we'd either need to go through the SymbolFileDWARF to get the full logic for resolving a DIERef, or use the fact that ToDIERef already looks up the correct unit while computing its result. This patch does the latter. This bug manifested itself in not being able to find type definitions for types in namespaces, so I've modified one of our type resolving test cases to run with debug_names, and added a namespaced class into it (it originally contained only a top-level class). >From 1c36a0c63f2c7c69048de36ab524cc8df7056704 Mon Sep 17 00:00:00 2001 From: Pavel Labath Date: Mon, 20 May 2024 12:30:46 + Subject: [PATCH] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf DWARFDebugInfo only knows how to resolve references in its own file, but in split dwarf, the index entries will refer to DIEs in the separate (DWO) file. To resolve the DIERef correctly we'd either need to go through the SymbolFileDWARF to get the full logic for resolving a DIERef, or use the fact that ToDIERef already looks up the correct unit while computing its result. This patch does the latter. This bug manifested itself in not being able to find type definitions for types in namespaces, so I've modified one of our type resolving test cases to run with debug_names, and added a namespaced class into it (it originally contained only a top-level class). --- .../SymbolFile/DWARF/DWARFDebugInfo.cpp | 6 --- .../Plugins/SymbolFile/DWARF/DWARFDebugInfo.h | 5 --- .../SymbolFile/DWARF/DebugNamesDWARFIndex.cpp | 27 -- .../SymbolFile/DWARF/DebugNamesDWARFIndex.h | 2 +- .../API/lang/cpp/limit-debug-info/Makefile| 2 - .../TestWithLimitDebugInfo.py | 36 +- .../API/lang/cpp/limit-debug-info/base.cpp| 9 ++--- .../test/API/lang/cpp/limit-debug-info/base.h | 22 --- .../API/lang/cpp/limit-debug-info/derived.cpp | 11 +++--- .../API/lang/cpp/limit-debug-info/derived.h | 37 ++- .../API/lang/cpp/limit-debug-info/main.cpp| 6 +-- .../SymbolFile/DWARF/DWARFDIETest.cpp | 24 ++-- 12 files changed, 100 insertions(+), 87 deletions(-) diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp index 44febcfac3b00..d28da728728e5 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp @@ -259,9 +259,3 @@ DWARFDebugInfo::GetDIE(const DIERef &die_ref) { return cu->GetNonSkeletonUnit().GetDIE(die_ref.die_offset()); return DWARFDIE(); // Not found } - -llvm::StringRef DWARFDebugInfo::PeekDIEName(const DIERef &die_ref) { - if (DWARFUnit *cu = GetUnit(die_ref)) -return cu->GetNonSkeletonUnit().PeekDIEName(die_ref.die_offset()); - return llvm::StringRef(); -} diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h index c1f0cb0203fb7..456ebd908ccb2 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h @@ -44,11 +44,6 @@ class DWARFDebugInfo { bool ContainsTypeUnits(); DWARFDIE GetDIE(const DIERef &die_ref); - /// Returns the AT_Name of this DIE, if it exists, without parsing the entire - /// compile unit. An empty is string is returned upon error or if the - /// attribute is not present. - llvm::StringRef PeekDIEName(const DIERef &die_ref); - enum { eDumpFlag_Verbose = (1 << 0), // Verbose dumping eDumpFlag_ShowForm = (1 << 1), // Show the DW_form type diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp index 4da0d56fdcacb..7fff5f52dfd79 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp @@ -9,7 +9,7 @@ #include "Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.h" #include "Plugins/SymbolFile/DWARF/DWARFDebugInfo.h" #include "Plugins/SymbolFile/DWARF/DWARFDeclContext.h" -#include "Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h" +#include "Plugins/SymbolFile/DWARF/LogChannelDWARF.h" #include "lldb/Core/Module.h" #include "lldb/Utility/RegularExpression.h" #include "lldb/Utility/Stream.h" @@ -48,26 +48,29 @@ DebugNamesDWARFIndex::GetUnits(const DebugNames &debug_names) { return result; } -std::optional -DebugNamesDWARFIndex::ToDIERef(const DebugNames::Entry &entry) const { +DWARFUnit *DebugNamesDWARFIndex::GetNonSkeletonUnit(const DebugNames::Entry &entry) const { // Look for a DWARF unit offset (CU offset or local TU offset) as they are // both offsets into th
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
llvmbot wrote: @llvm/pr-subscribers-lldb Author: Pavel Labath (labath) Changes DWARFDebugInfo only knows how to resolve references in its own file, but in split dwarf, the index entries will refer to DIEs in the separate (DWO) file. To resolve the DIERef correctly we'd either need to go through the SymbolFileDWARF to get the full logic for resolving a DIERef, or use the fact that ToDIERef already looks up the correct unit while computing its result. This patch does the latter. This bug manifested itself in not being able to find type definitions for types in namespaces, so I've modified one of our type resolving test cases to run with debug_names, and added a namespaced class into it (it originally contained only a top-level class). --- Full diff: https://github.com/llvm/llvm-project/pull/92745.diff 12 Files Affected: - (modified) lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp (-6) - (modified) lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h (-5) - (modified) lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp (+15-12) - (modified) lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.h (+1-1) - (modified) lldb/test/API/lang/cpp/limit-debug-info/Makefile (-2) - (modified) lldb/test/API/lang/cpp/limit-debug-info/TestWithLimitDebugInfo.py (+18-18) - (modified) lldb/test/API/lang/cpp/limit-debug-info/base.cpp (+4-5) - (modified) lldb/test/API/lang/cpp/limit-debug-info/base.h (+16-6) - (modified) lldb/test/API/lang/cpp/limit-debug-info/derived.cpp (+5-6) - (modified) lldb/test/API/lang/cpp/limit-debug-info/derived.h (+27-10) - (modified) lldb/test/API/lang/cpp/limit-debug-info/main.cpp (+2-4) - (modified) lldb/unittests/SymbolFile/DWARF/DWARFDIETest.cpp (+12-12) ``diff diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp index 44febcfac3b00..d28da728728e5 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp @@ -259,9 +259,3 @@ DWARFDebugInfo::GetDIE(const DIERef &die_ref) { return cu->GetNonSkeletonUnit().GetDIE(die_ref.die_offset()); return DWARFDIE(); // Not found } - -llvm::StringRef DWARFDebugInfo::PeekDIEName(const DIERef &die_ref) { - if (DWARFUnit *cu = GetUnit(die_ref)) -return cu->GetNonSkeletonUnit().PeekDIEName(die_ref.die_offset()); - return llvm::StringRef(); -} diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h index c1f0cb0203fb7..456ebd908ccb2 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h @@ -44,11 +44,6 @@ class DWARFDebugInfo { bool ContainsTypeUnits(); DWARFDIE GetDIE(const DIERef &die_ref); - /// Returns the AT_Name of this DIE, if it exists, without parsing the entire - /// compile unit. An empty is string is returned upon error or if the - /// attribute is not present. - llvm::StringRef PeekDIEName(const DIERef &die_ref); - enum { eDumpFlag_Verbose = (1 << 0), // Verbose dumping eDumpFlag_ShowForm = (1 << 1), // Show the DW_form type diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp index 4da0d56fdcacb..7fff5f52dfd79 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp @@ -9,7 +9,7 @@ #include "Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.h" #include "Plugins/SymbolFile/DWARF/DWARFDebugInfo.h" #include "Plugins/SymbolFile/DWARF/DWARFDeclContext.h" -#include "Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h" +#include "Plugins/SymbolFile/DWARF/LogChannelDWARF.h" #include "lldb/Core/Module.h" #include "lldb/Utility/RegularExpression.h" #include "lldb/Utility/Stream.h" @@ -48,26 +48,29 @@ DebugNamesDWARFIndex::GetUnits(const DebugNames &debug_names) { return result; } -std::optional -DebugNamesDWARFIndex::ToDIERef(const DebugNames::Entry &entry) const { +DWARFUnit *DebugNamesDWARFIndex::GetNonSkeletonUnit(const DebugNames::Entry &entry) const { // Look for a DWARF unit offset (CU offset or local TU offset) as they are // both offsets into the .debug_info section. std::optional unit_offset = entry.getCUOffset(); if (!unit_offset) { unit_offset = entry.getLocalTUOffset(); if (!unit_offset) - return std::nullopt; + return nullptr; } DWARFUnit *cu = m_debug_info.GetUnitAtOffset(DIERef::Section::DebugInfo, *unit_offset); - if (!cu) -return std::nullopt; + return cu ? &cu->GetNonSkeletonUnit() : nullptr; +} - cu = &cu->GetNonSkeletonUnit(); +std::optional +DebugNamesDWARFIndex::ToDIERef(const DebugNames::Entry &entry) const { + DWARFUnit *unit = GetNonSkeletonUnit(entry); + if (!unit) +return std::nullopt; if (std::optional die_of
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
github-actions[bot] wrote: :warning: Python code formatter, darker found issues in your code. :warning: You can test this locally with the following command: ``bash darker --check --diff -r da6a0b7af29a222b2e16a10155b49d4fafe967f3...1c36a0c63f2c7c69048de36ab524cc8df7056704 lldb/test/API/lang/cpp/limit-debug-info/TestWithLimitDebugInfo.py `` View the diff from darker here. ``diff --- TestWithLimitDebugInfo.py 2024-05-20 12:56:24.00 + +++ TestWithLimitDebugInfo.py 2024-05-20 13:07:51.177002 + @@ -14,12 +14,16 @@ # Load the executable target = self.dbg.CreateTarget(exe_path) self.assertTrue(target.IsValid(), VALID_TARGET) # Break on main function -lldbutil.run_break_set_by_file_and_line(self, "derived.h", line_number("derived.h", "// break1")) -lldbutil.run_break_set_by_file_and_line(self, "derived.h", line_number("derived.h", "// break2")) +lldbutil.run_break_set_by_file_and_line( +self, "derived.h", line_number("derived.h", "// break1") +) +lldbutil.run_break_set_by_file_and_line( +self, "derived.h", line_number("derived.h", "// break2") +) # Launch the process process = target.LaunchSimple(None, None, self.get_process_working_directory()) self.assertTrue(process.IsValid(), PROCESS_IS_VALID) @@ -40,6 +44,8 @@ def test_default(self): self._run_test(dict(CFLAGS_EXTRAS="$(LIMIT_DEBUG_INFO_FLAGS)")) @add_test_categories(["dwarf", "dwo"]) def test_debug_names(self): -self._run_test(dict(CFLAGS_EXTRAS="$(LIMIT_DEBUG_INFO_FLAGS) -gdwarf-5 -gpubnames")) +self._run_test( +dict(CFLAGS_EXTRAS="$(LIMIT_DEBUG_INFO_FLAGS) -gdwarf-5 -gpubnames") +) `` https://github.com/llvm/llvm-project/pull/92745 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
github-actions[bot] wrote: :warning: C/C++ code formatter, clang-format found issues in your code. :warning: You can test this locally with the following command: ``bash git-clang-format --diff da6a0b7af29a222b2e16a10155b49d4fafe967f3 1c36a0c63f2c7c69048de36ab524cc8df7056704 -- lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.h lldb/test/API/lang/cpp/limit-debug-info/base.cpp lldb/test/API/lang/cpp/limit-debug-info/base.h lldb/test/API/lang/cpp/limit-debug-info/derived.cpp lldb/test/API/lang/cpp/limit-debug-info/derived.h lldb/test/API/lang/cpp/limit-debug-info/main.cpp lldb/unittests/SymbolFile/DWARF/DWARFDIETest.cpp `` View the diff from clang-format here. ``diff diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp index 7fff5f52df..79400e36e0 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp @@ -48,7 +48,8 @@ DebugNamesDWARFIndex::GetUnits(const DebugNames &debug_names) { return result; } -DWARFUnit *DebugNamesDWARFIndex::GetNonSkeletonUnit(const DebugNames::Entry &entry) const { +DWARFUnit * +DebugNamesDWARFIndex::GetNonSkeletonUnit(const DebugNames::Entry &entry) const { // Look for a DWARF unit offset (CU offset or local TU offset) as they are // both offsets into the .debug_info section. std::optional unit_offset = entry.getCUOffset(); `` https://github.com/llvm/llvm-project/pull/92745 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
https://github.com/labath updated https://github.com/llvm/llvm-project/pull/92745 >From ae72d530c723a8d0fb2eac38224e8cf74cc43e70 Mon Sep 17 00:00:00 2001 From: Pavel Labath Date: Mon, 20 May 2024 12:30:46 + Subject: [PATCH] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf DWARFDebugInfo only knows how to resolve references in its own file, but in split dwarf, the index entries will refer to DIEs in the separate (DWO) file. To resolve the DIERef correctly we'd either need to go through the SymbolFileDWARF to get the full logic for resolving a DIERef, or use the fact that ToDIERef already looks up the correct unit while computing its result. This patch does the latter. This bug manifested itself in not being able to find type definitions for types in namespaces, so I've modified one of our type resolving test cases to run with debug_names, and added a namespaced class into it (it originally contained only a top-level class). --- .../SymbolFile/DWARF/DWARFDebugInfo.cpp | 6 --- .../Plugins/SymbolFile/DWARF/DWARFDebugInfo.h | 5 --- .../SymbolFile/DWARF/DebugNamesDWARFIndex.cpp | 28 +++-- .../SymbolFile/DWARF/DebugNamesDWARFIndex.h | 2 +- .../API/lang/cpp/limit-debug-info/Makefile| 2 - .../TestWithLimitDebugInfo.py | 40 +++ .../API/lang/cpp/limit-debug-info/base.cpp| 9 ++--- .../test/API/lang/cpp/limit-debug-info/base.h | 22 +++--- .../API/lang/cpp/limit-debug-info/derived.cpp | 11 +++-- .../API/lang/cpp/limit-debug-info/derived.h | 37 - .../API/lang/cpp/limit-debug-info/main.cpp| 6 +-- .../SymbolFile/DWARF/DWARFDIETest.cpp | 24 +-- 12 files changed, 106 insertions(+), 86 deletions(-) diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp index 44febcfac3b00..d28da728728e5 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.cpp @@ -259,9 +259,3 @@ DWARFDebugInfo::GetDIE(const DIERef &die_ref) { return cu->GetNonSkeletonUnit().GetDIE(die_ref.die_offset()); return DWARFDIE(); // Not found } - -llvm::StringRef DWARFDebugInfo::PeekDIEName(const DIERef &die_ref) { - if (DWARFUnit *cu = GetUnit(die_ref)) -return cu->GetNonSkeletonUnit().PeekDIEName(die_ref.die_offset()); - return llvm::StringRef(); -} diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h index c1f0cb0203fb7..456ebd908ccb2 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfo.h @@ -44,11 +44,6 @@ class DWARFDebugInfo { bool ContainsTypeUnits(); DWARFDIE GetDIE(const DIERef &die_ref); - /// Returns the AT_Name of this DIE, if it exists, without parsing the entire - /// compile unit. An empty is string is returned upon error or if the - /// attribute is not present. - llvm::StringRef PeekDIEName(const DIERef &die_ref); - enum { eDumpFlag_Verbose = (1 << 0), // Verbose dumping eDumpFlag_ShowForm = (1 << 1), // Show the DW_form type diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp index 4da0d56fdcacb..79400e36e04f3 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.cpp @@ -9,7 +9,7 @@ #include "Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.h" #include "Plugins/SymbolFile/DWARF/DWARFDebugInfo.h" #include "Plugins/SymbolFile/DWARF/DWARFDeclContext.h" -#include "Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h" +#include "Plugins/SymbolFile/DWARF/LogChannelDWARF.h" #include "lldb/Core/Module.h" #include "lldb/Utility/RegularExpression.h" #include "lldb/Utility/Stream.h" @@ -48,26 +48,30 @@ DebugNamesDWARFIndex::GetUnits(const DebugNames &debug_names) { return result; } -std::optional -DebugNamesDWARFIndex::ToDIERef(const DebugNames::Entry &entry) const { +DWARFUnit * +DebugNamesDWARFIndex::GetNonSkeletonUnit(const DebugNames::Entry &entry) const { // Look for a DWARF unit offset (CU offset or local TU offset) as they are // both offsets into the .debug_info section. std::optional unit_offset = entry.getCUOffset(); if (!unit_offset) { unit_offset = entry.getLocalTUOffset(); if (!unit_offset) - return std::nullopt; + return nullptr; } DWARFUnit *cu = m_debug_info.GetUnitAtOffset(DIERef::Section::DebugInfo, *unit_offset); - if (!cu) -return std::nullopt; + return cu ? &cu->GetNonSkeletonUnit() : nullptr; +} - cu = &cu->GetNonSkeletonUnit(); +std::optional +DebugNamesDWARFIndex::ToDIERef(const DebugNames::Entry &entry) const { + DWARFUnit *unit = GetNonSkeletonUnit(entry); + if (!unit) +return std::nullopt; if (std::optional die_offset = entry.getDIEUnit
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
https://github.com/felipepiovezan edited https://github.com/llvm/llvm-project/pull/92745 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
@@ -9,7 +9,7 @@ #include "Plugins/SymbolFile/DWARF/DebugNamesDWARFIndex.h" #include "Plugins/SymbolFile/DWARF/DWARFDebugInfo.h" #include "Plugins/SymbolFile/DWARF/DWARFDeclContext.h" -#include "Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h" +#include "Plugins/SymbolFile/DWARF/LogChannelDWARF.h" felipepiovezan wrote: Is this actually needed? https://github.com/llvm/llvm-project/pull/92745 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb/dwarf] Fix DW_IDX_parent processing for split dwarf (PR #92745)
https://github.com/felipepiovezan approved this pull request. Great catch and fix! Thanks for doing this https://github.com/llvm/llvm-project/pull/92745 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Added "port" property to vscode "attach" command. (PR #91570)
@@ -1572,6 +1572,15 @@ def findBuiltClang(self): return os.environ["CC"] +def getBuiltinServerTool(self, server_tool): +# Tries to find simulation/lldb-server/gdbserver tool at the same folder as the lldb. +lldb_dir = os.path.dirname(lldbtest_config.lldbExec) +path = shutil.which(server_tool, path=lldb_dir) +if path is not None: +return path + +return "" santhoshe447 wrote: Agreed with this comment. I would like to modify this function to get the lldb-server/gdbserver based on OS. Is this fine ? https://github.com/llvm/llvm-project/pull/91570 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
feg208 wrote: Hello all. I am wondering what I can do to advance this patch? I think it is required to support process save-core in linux for lldb. I'd love to move this before adding static methods in ThreadEfCore.h to produce populated prpsinfo and prstatus structs for inclusion in a generated corefile. Is there someone else I should include on review here? @JDevlieghere? I am happy to amend this in whatever way the community thinks works best for lldb. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Added "port" property to vscode "attach" command. (PR #91570)
@@ -0,0 +1,146 @@ +""" +Test lldb-dap "port" configuration to "attach" request +""" + + +import dap_server +from lldbsuite.test.decorators import * +from lldbsuite.test.lldbtest import * +from lldbsuite.test import lldbutil +from lldbsuite.test import lldbplatformutil +import lldbgdbserverutils +import lldbdap_testcase +import os +import shutil +import subprocess +import tempfile +import threading +import time +import sys + + +class TestDAP_attachByPortNum(lldbdap_testcase.DAPTestCaseBase): +def runTargetProgramOnPort(self, port=None, program=None): +server_tool = None +if lldbplatformutil.getPlatform() == "linux": +server_tool = lldbgdbserverutils.get_lldb_server_exe() +if server_tool is None: +self.dap_server.request_disconnect(terminateDebuggee=True) +self.assertIsNotNone(server_tool, "lldb-server not found.") +server_tool += " g localhost:" + port + " " +elif lldbplatformutil.getPlatform() == "macosx": +server_tool = lldbgdbserverutils.get_debugserver_exe() +if server_tool is None: +self.dap_server.request_disconnect(terminateDebuggee=True) +self.assertIsNotNone(server_tool, "debugserver not found.") +server_tool += " --listen localhost:" + port + " " santhoshe447 wrote: Agreed with your comment. I think it would be better to move this into lldbtest.py instead of lldb_testcase,py as it has all utility funtions. https://github.com/llvm/llvm-project/pull/91570 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Added "port" property to vscode "attach" command. (PR #91570)
@@ -0,0 +1,146 @@ +""" +Test lldb-dap "port" configuration to "attach" request +""" + + +import dap_server +from lldbsuite.test.decorators import * +from lldbsuite.test.lldbtest import * +from lldbsuite.test import lldbutil +from lldbsuite.test import lldbplatformutil +import lldbgdbserverutils +import lldbdap_testcase +import os +import shutil +import subprocess +import tempfile +import threading +import time +import sys + + +class TestDAP_attachByPortNum(lldbdap_testcase.DAPTestCaseBase): +def runTargetProgramOnPort(self, port=None, program=None): +server_tool = None +if lldbplatformutil.getPlatform() == "linux": +server_tool = lldbgdbserverutils.get_lldb_server_exe() +if server_tool is None: +self.dap_server.request_disconnect(terminateDebuggee=True) +self.assertIsNotNone(server_tool, "lldb-server not found.") +server_tool += " g localhost:" + port + " " +elif lldbplatformutil.getPlatform() == "macosx": +server_tool = lldbgdbserverutils.get_debugserver_exe() +if server_tool is None: +self.dap_server.request_disconnect(terminateDebuggee=True) +self.assertIsNotNone(server_tool, "debugserver not found.") +server_tool += " --listen localhost:" + port + " " + +self.process = subprocess.Popen( +[server_tool + program], +shell=True, +stdin=subprocess.PIPE, +stdout=subprocess.PIPE, +stderr=subprocess.PIPE, +) + +return self.process + +def set_and_hit_breakpoint(self, continueToExit=True): +source = "main.c" +main_source_path = os.path.join(os.getcwd(), source) +breakpoint1_line = line_number(main_source_path, "// breakpoint 1") +lines = [breakpoint1_line] +# Set breakpoint in the thread function so we can step the threads +breakpoint_ids = self.set_source_breakpoints(main_source_path, lines) +self.assertEqual( +len(breakpoint_ids), len(lines), "expect correct number of breakpoints" +) +self.continue_to_breakpoints(breakpoint_ids) +if continueToExit: +self.continue_to_exit() + +@skipIfWindows +@skipIfNetBSD # Hangs on NetBSD as well santhoshe447 wrote: This test case is designed to be verified only on Linux and macOS. https://github.com/llvm/llvm-project/pull/91570 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Added "port" property to vscode "attach" command. (PR #91570)
https://github.com/santhoshe447 updated https://github.com/llvm/llvm-project/pull/91570 >From 960351c9abf51f42d92604ac6297aa5b76ddfba5 Mon Sep 17 00:00:00 2001 From: Santhosh Kumar Ellendula Date: Fri, 17 Nov 2023 15:09:10 +0530 Subject: [PATCH 1/8] [lldb][test] Add the ability to extract the variable value out of the summary. --- .../Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py | 3 +++ 1 file changed, 3 insertions(+) diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py index 9d79872b029a3..0cf9d4fde4948 100644 --- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py +++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py @@ -195,6 +195,9 @@ def collect_console(self, duration): def get_local_as_int(self, name, threadId=None): value = self.dap_server.get_local_variable_value(name, threadId=threadId) +# 'value' may have the variable value and summary. +# Extract the variable value since summary can have nonnumeric characters. +value = value.split(" ")[0] if value.startswith("0x"): return int(value, 16) elif value.startswith("0"): >From ab44a6991c5bc8ac5764c3f71cbe3acc747b3776 Mon Sep 17 00:00:00 2001 From: Santhosh Kumar Ellendula Date: Fri, 3 May 2024 02:47:05 -0700 Subject: [PATCH 2/8] [lldb-dap] Added "port" property to vscode "attach" command. Adding a "port" property to the VsCode "attach" command likely extends the functionality of the debugger configuratiuon to allow attaching to a process using PID or PORT number. Currently, the "Attach" configuration lets the user specify a pid. We tell the user to use the attachCommands property to run "gdb-remote ". Followed the below conditions for "attach" command with "port" and "pid" We should add a "port" property. If port is specified and pid is not, use that port to attach. If both port and pid are specified, return an error saying that the user can't specify both pid and port. Ex - launch.json { "version": "0.2.0", "configurations": [ { "name": "lldb-dap Debug", "type": "lldb-dap", "request": "attach", "port":1234, "program": "${workspaceFolder}/a.out", "args": [], "stopOnEntry": false, "cwd": "${workspaceFolder}", "env": [], } ] } --- lldb/include/lldb/lldb-defines.h | 1 + .../Python/lldbsuite/test/lldbtest.py | 9 ++ .../test/tools/lldb-dap/dap_server.py | 6 + .../test/tools/lldb-dap/lldbdap_testcase.py | 20 +++ .../attach/TestDAP_attachByPortNum.py | 120 ++ lldb/tools/lldb-dap/lldb-dap.cpp | 36 +- lldb/tools/lldb-dap/package.json | 11 ++ 7 files changed, 199 insertions(+), 4 deletions(-) create mode 100644 lldb/test/API/tools/lldb-dap/attach/TestDAP_attachByPortNum.py diff --git a/lldb/include/lldb/lldb-defines.h b/lldb/include/lldb/lldb-defines.h index c7bd019c5c90e..a1e6ee2ce468c 100644 --- a/lldb/include/lldb/lldb-defines.h +++ b/lldb/include/lldb/lldb-defines.h @@ -96,6 +96,7 @@ #define LLDB_INVALID_QUEUE_ID 0 #define LLDB_INVALID_CPU_ID UINT32_MAX #define LLDB_INVALID_WATCHPOINT_RESOURCE_ID UINT32_MAX +#define LLDB_INVALID_PORT_NUMBER 0 /// CPU Type definitions #define LLDB_ARCH_DEFAULT "systemArch" diff --git a/lldb/packages/Python/lldbsuite/test/lldbtest.py b/lldb/packages/Python/lldbsuite/test/lldbtest.py index 5fd686c143e9f..fb3cd22959df2 100644 --- a/lldb/packages/Python/lldbsuite/test/lldbtest.py +++ b/lldb/packages/Python/lldbsuite/test/lldbtest.py @@ -1572,6 +1572,15 @@ def findBuiltClang(self): return os.environ["CC"] +def getBuiltServerTool(self, server_tool): +# Tries to find simulation/lldb-server/gdbserver tool at the same folder as the lldb. +lldb_dir = os.path.dirname(lldbtest_config.lldbExec) +path = shutil.which(server_tool, path=lldb_dir) +if path is not None: +return path + +return "" + def yaml2obj(self, yaml_path, obj_path, max_size=None): """ Create an object file at the given path from a yaml file. diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py index 5838281bcb1a1..96d312565f953 100644 --- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py +++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py @@ -568,6 +568,8 @@ def request_attach( coreFile=None, postRunCommands=None, sourceMap=None, +port=None, +hostname=None ): args_dict = {} if pid is not None: @@ -597,6 +599,10 @@ def request_attach( args_dict["postRunCommands"] = postRunComman
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
https://github.com/feg208 updated https://github.com/llvm/llvm-project/pull/91544 >From e7b1cf56dae4c93b871aeeeafc5b40752baf823e Mon Sep 17 00:00:00 2001 From: Fred Grim Date: Wed, 8 May 2024 15:36:16 -0700 Subject: [PATCH] [lldb] Adds additional fields to ProcessInfo To implement SaveCore for elf binaries we need to populate some additional fields in the prpsinfo struct. Those fields are the nice value of the process whose core is to be taken as well as a boolean flag indicating whether or not that process is a zombie. This commit adds those as well as tests to ensure that the values are consistent with expectations --- lldb/include/lldb/Utility/ProcessInfo.h | 52 + lldb/source/Host/linux/Host.cpp | 32 +++ lldb/source/Utility/ProcessInfo.cpp | 11 -- lldb/unittests/Host/linux/HostTest.cpp | 21 ++ 4 files changed, 89 insertions(+), 27 deletions(-) diff --git a/lldb/include/lldb/Utility/ProcessInfo.h b/lldb/include/lldb/Utility/ProcessInfo.h index 54ac000dc7fc2..6844211f05c74 100644 --- a/lldb/include/lldb/Utility/ProcessInfo.h +++ b/lldb/include/lldb/Utility/ProcessInfo.h @@ -15,6 +15,7 @@ #include "lldb/Utility/FileSpec.h" #include "lldb/Utility/NameMatches.h" #include "lldb/Utility/StructuredData.h" +#include #include namespace lldb_private { @@ -147,8 +148,7 @@ class ProcessInstanceInfo : public ProcessInfo { ProcessInstanceInfo() = default; ProcessInstanceInfo(const char *name, const ArchSpec &arch, lldb::pid_t pid) - : ProcessInfo(name, arch, pid), m_euid(UINT32_MAX), m_egid(UINT32_MAX), -m_parent_pid(LLDB_INVALID_PROCESS_ID) {} + : ProcessInfo(name, arch, pid) {} void Clear() { ProcessInfo::Clear(); @@ -195,24 +195,26 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { @@ -220,12 +222,13 @@ class ProcessInstanceInfo : public ProcessInfo { } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { @@ -233,10 +236,25 @@ class ProcessInstanceInfo : public ProcessInfo { } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + bool PriorityValueIsValid() const; + + void SetIsZombie(bool is_zombie) { m_zombie = is_zombie; } + + bool IsZombieValid() const { return m_zombie.has_value(); } + + bool IsZombie() const { return m_zombie.value(); } + void Dump(Stream &s, UserIDResolver &resolver) const; static void DumpTableHeader(Stream &s, bool show_args, bool verbose); @@ -250,10 +268,12 @@ class ProcessInstanceInfo : public ProcessInfo { lldb::pid_t m_parent_pid = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_group_id = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_session_id = LLDB_INVALID_PROCESS_ID; - struct timespec m_user_time {}; - struct timespec m_system_time {}; - struct timespec m_cumulative_user_time {}; - struct timespec m_cumulative_system_time {}; + std::optional m_user_time = std::nullopt; + std::optional m_system_time = std::nullopt; + std::optional m_cumulative_user_time = std::nullopt
[Lldb-commits] [lldb] [lldb-dap] Don't send expanded descriptions for "hover" expressions (PR #92726)
https://github.com/ashgti approved this pull request. https://github.com/llvm/llvm-project/pull/92726 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Don't send expanded descriptions for "hover" expressions (PR #92726)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/92726 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
@@ -1427,8 +1440,30 @@ void Debugger::SetLoggingCallback(lldb::LogOutputCallback log_callback, void Debugger::SetDestroyCallback( lldb_private::DebuggerDestroyCallback destroy_callback, void *baton) { - m_destroy_callback = destroy_callback; - m_destroy_callback_baton = baton; + std::lock_guard guard(m_destroy_callback_mutex); + m_destroy_callbacks.clear(); + const lldb::destroy_callback_token_t token = m_destroy_callback_next_token++; + m_destroy_callbacks.emplace_back(token, destroy_callback, baton); +} + +lldb::destroy_callback_token_t Debugger::AddDestroyCallback( +lldb_private::DebuggerDestroyCallback destroy_callback, void *baton) { + std::lock_guard guard(m_destroy_callback_mutex); + const lldb::destroy_callback_token_t token = m_destroy_callback_next_token++; + m_destroy_callbacks.emplace_back(token, destroy_callback, baton); + return token; +} + +bool Debugger::RemoveDestroyCallback(lldb::destroy_callback_token_t token) { + std::lock_guard guard(m_destroy_callback_mutex); + for (auto it = m_destroy_callbacks.begin(); it != m_destroy_callbacks.end(); + ++it) { +if (std::get<0>(*it) == token) { clayborg wrote: Convert to use the new `DestroyCallbackInfo` struct members. https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
@@ -731,8 +747,12 @@ class Debugger : public std::enable_shared_from_this, lldb::TargetSP m_dummy_target_sp; Diagnostics::CallbackID m_diagnostics_callback_id; - lldb_private::DebuggerDestroyCallback m_destroy_callback = nullptr; - void *m_destroy_callback_baton = nullptr; + std::mutex m_destroy_callback_mutex; + lldb::destroy_callback_token_t m_destroy_callback_next_token = 0; + typedef std::tuple clayborg wrote: Instead of a tuple, please create a struct type. Using tuples isn't very readable even though it works: ``` struct DestroyCallbackInfo { lldb::callback_token_t token; lldb_private::DebuggerDestroyCallback callback; void *baton; }; ``` https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
@@ -62,12 +62,15 @@ typedef void *thread_arg_t; // Host thread argument type typedef void *thread_result_t; // Host thread result type typedef void *(*thread_func_t)(void *); // Host thread function type typedef int pipe_t; // Host pipe type +typedef int destroy_callback_token_t; // Debugger destroy callback token type #endif // _WIN32 #define LLDB_INVALID_PROCESS ((lldb::process_t)-1) #define LLDB_INVALID_HOST_THREAD ((lldb::thread_t)NULL) #define LLDB_INVALID_PIPE ((lldb::pipe_t)-1) +#define LLDB_INVALID_DESTROY_CALLBACK_TOKEN \ + ((lldb::destroy_callback_token_t) - 1) clayborg wrote: Remove "DESTROY" from bot the #define and _t type: ``` #define LLDB_INVALID_CALLBACK_TOKEN ((lldb::callback_token_t) - 1) ``` https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
@@ -731,8 +747,12 @@ class Debugger : public std::enable_shared_from_this, lldb::TargetSP m_dummy_target_sp; Diagnostics::CallbackID m_diagnostics_callback_id; - lldb_private::DebuggerDestroyCallback m_destroy_callback = nullptr; - void *m_destroy_callback_baton = nullptr; + std::mutex m_destroy_callback_mutex; + lldb::destroy_callback_token_t m_destroy_callback_next_token = 0; + typedef std::tuple + DebuggerDestroyCallbackTuple; + llvm::SmallVector m_destroy_callbacks; clayborg wrote: llvm::SmallVector m_destroy_callbacks; https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
@@ -62,12 +62,15 @@ typedef void *thread_arg_t; // Host thread argument type typedef void *thread_result_t; // Host thread result type typedef void *(*thread_func_t)(void *); // Host thread function type typedef int pipe_t; // Host pipe type +typedef int destroy_callback_token_t; // Debugger destroy callback token type clayborg wrote: Since we are adding this to the public API, we should remove the "destroy" from this so we could re-use this for other callback tokens. So change this to: ``` typedef int callback_token_t; ``` And remove the comment since making a comment of `// Callback token type` doesn't really tell you anything more than the name already does. The reason being we don't want to have to add a ton of callback token types for every callback we might want to register in the future (`process_callback_token_t`, `thread_callback_token_t`, ...). We can just use one for all of them in the future. https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
https://github.com/clayborg commented: Just a few comments to fixup as mentioned and this is good to go. https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
@@ -766,6 +771,14 @@ class CommandInterpreter : public Broadcaster, CommandUsageMap m_command_usages; StreamString m_transcript_stream; + + /// Contains a list of handled commands and their details. Each element in clayborg wrote: We should mention the new setting that is required for this to become populated. https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
https://github.com/clayborg edited https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
@@ -766,6 +771,14 @@ class CommandInterpreter : public Broadcaster, CommandUsageMap m_command_usages; StreamString m_transcript_stream; clayborg wrote: We should mention in a comment that this will only be filled in if the setting is true. https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
JDevlieghere wrote: > Hello all. I am wondering what I can do to advance this patch? I think it is > required to support process save-core in linux for lldb. I'd love to move > this before adding static methods in ThreadEfCore.h to produce populated > prpsinfo and prstatus structs for inclusion in a generated corefile. Is there > someone else I should include on review here? @JDevlieghere? I am happy to > amend this in whatever way the community thinks works best for lldb. A message like this that the PR is ready for re-review should be all you need. Several folks left comments and they might be waiting for all of them to be addressed before they take another look. If you don't hear back within a week, you can ping the patch to get reviewer's attention. There's some more info here: https://llvm.org/docs/CodeReview.html#lgtm-how-a-patch-is-accepted https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
feg208 wrote: > A message like this that the PR is ready for re-review should be all you > need. Several folks left comments and they might be waiting for all of them > to be addressed before they take another look. Ok. @clayborg I think I have addressed your concerns but I'd love another look as you have time. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Improve performance of .debug_names lookups when DW_IDX_parent attributes are used (PR #91808)
clayborg wrote: > What's an actual test case for this issue? The example given above doesn't > look like it'd produce entries for the declaration of ios_base? Like here's > something that looks equivalent, but is complete, and doesn't have a > DW_IDX_parent on the nested typedef entry in the index: > https://godbolt.org/z/efjbze3x1 > > it'd be good to have a reproducer for this to motivate the discussion... I will see what I can do to repro with a minimal test case. But I do believe that this PR should go in as right now we have binaries with thousands of entries that are being found from the top down from a name entry and causes tons of bogus type resolving lookups to happen. https://github.com/llvm/llvm-project/pull/91808 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
https://github.com/mbucko updated https://github.com/llvm/llvm-project/pull/92014 >From b29f3fcea87c3ce7cf65de14dc924f1862c63098 Mon Sep 17 00:00:00 2001 From: Miro Bucko Date: Fri, 10 May 2024 12:42:03 -0700 Subject: [PATCH] Add AddressRange to SB API Summary: This adds new SB API calls and classes to allow a user of the SB API to obtain an address range from SBFunction and SBBlock. Test Plan: llvm-lit -sv llvm-project/lldb/test/API/python_api/address_range/TestAddressRange.py Reviewers: clayborg Subscribers: lldb-commits Tasks: Tags: --- lldb/bindings/headers.swig| 2 + .../interface/SBAddressRangeDocstrings.i | 3 + .../interface/SBAddressRangeExtensions.i | 11 + .../interface/SBAddressRangeListDocstrings.i | 3 + .../interface/SBAddressRangeListExtensions.i | 28 +++ lldb/bindings/interfaces.swig | 6 + lldb/include/lldb/API/LLDB.h | 2 + lldb/include/lldb/API/SBAddress.h | 1 + lldb/include/lldb/API/SBAddressRange.h| 65 ++ lldb/include/lldb/API/SBAddressRangeList.h| 54 + lldb/include/lldb/API/SBBlock.h | 4 + lldb/include/lldb/API/SBDefines.h | 2 + lldb/include/lldb/API/SBFunction.h| 3 + lldb/include/lldb/API/SBStream.h | 2 + lldb/include/lldb/API/SBTarget.h | 1 + lldb/include/lldb/Core/AddressRange.h | 14 ++ lldb/include/lldb/Core/AddressRangeListImpl.h | 51 + lldb/include/lldb/Symbol/Block.h | 2 + lldb/include/lldb/lldb-forward.h | 3 + lldb/source/API/CMakeLists.txt| 2 + lldb/source/API/SBAddressRange.cpp| 103 + lldb/source/API/SBAddressRangeList.cpp| 91 lldb/source/API/SBBlock.cpp | 10 + lldb/source/API/SBFunction.cpp| 14 ++ lldb/source/Core/AddressRange.cpp | 40 lldb/source/Core/AddressRangeListImpl.cpp | 50 lldb/source/Core/CMakeLists.txt | 1 + lldb/source/Symbol/Block.cpp | 16 ++ .../API/python_api/address_range/Makefile | 3 + .../address_range/TestAddressRange.py | 216 ++ .../API/python_api/address_range/main.cpp | 8 + 31 files changed, 811 insertions(+) create mode 100644 lldb/bindings/interface/SBAddressRangeDocstrings.i create mode 100644 lldb/bindings/interface/SBAddressRangeExtensions.i create mode 100644 lldb/bindings/interface/SBAddressRangeListDocstrings.i create mode 100644 lldb/bindings/interface/SBAddressRangeListExtensions.i create mode 100644 lldb/include/lldb/API/SBAddressRange.h create mode 100644 lldb/include/lldb/API/SBAddressRangeList.h create mode 100644 lldb/include/lldb/Core/AddressRangeListImpl.h create mode 100644 lldb/source/API/SBAddressRange.cpp create mode 100644 lldb/source/API/SBAddressRangeList.cpp create mode 100644 lldb/source/Core/AddressRangeListImpl.cpp create mode 100644 lldb/test/API/python_api/address_range/Makefile create mode 100644 lldb/test/API/python_api/address_range/TestAddressRange.py create mode 100644 lldb/test/API/python_api/address_range/main.cpp diff --git a/lldb/bindings/headers.swig b/lldb/bindings/headers.swig index ffdc3c31ec883..c91504604b6ac 100644 --- a/lldb/bindings/headers.swig +++ b/lldb/bindings/headers.swig @@ -8,6 +8,8 @@ %{ #include "lldb/lldb-public.h" #include "lldb/API/SBAddress.h" +#include "lldb/API/SBAddressRange.h" +#include "lldb/API/SBAddressRangeList.h" #include "lldb/API/SBAttachInfo.h" #include "lldb/API/SBBlock.h" #include "lldb/API/SBBreakpoint.h" diff --git a/lldb/bindings/interface/SBAddressRangeDocstrings.i b/lldb/bindings/interface/SBAddressRangeDocstrings.i new file mode 100644 index 0..650195704d73e --- /dev/null +++ b/lldb/bindings/interface/SBAddressRangeDocstrings.i @@ -0,0 +1,3 @@ +%feature("docstring", +"API clients can get address range information." +) lldb::SBAddressRange; diff --git a/lldb/bindings/interface/SBAddressRangeExtensions.i b/lldb/bindings/interface/SBAddressRangeExtensions.i new file mode 100644 index 0..9ff8e78080eb2 --- /dev/null +++ b/lldb/bindings/interface/SBAddressRangeExtensions.i @@ -0,0 +1,11 @@ +%extend lldb::SBAddressRange { +#ifdef SWIGPYTHON +%pythoncode%{ + def __repr__(self): +import lldb +stream = lldb.SBStream() +self.GetDescription(stream, lldb.target) +return stream.GetData() +%} +#endif +} diff --git a/lldb/bindings/interface/SBAddressRangeListDocstrings.i b/lldb/bindings/interface/SBAddressRangeListDocstrings.i new file mode 100644 index 0..e4b96b9ca5931 --- /dev/null +++ b/lldb/bindings/interface/SBAddressRangeListDocstrings.i @@ -0,0 +1,3 @@ +%feature("docstring", +"Represents a list of :py:class:`SBAddressRange`." +) lldb::SBAddressRangeList; diff --git a/lldb/bindings/interface/SBAddressRangeListExtensions.i b/lldb/
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
https://github.com/royitaqi updated https://github.com/llvm/llvm-project/pull/90703 >From 0fd67e2de7e702ce6f7353845454ea7ff9f980d6 Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Tue, 30 Apr 2024 21:35:49 -0700 Subject: [PATCH 01/19] Add SBCommandInterpreter::GetTranscript() --- lldb/include/lldb/API/SBCommandInterpreter.h | 12 +--- lldb/source/API/SBCommandInterpreter.cpp | 7 ++- 2 files changed, 15 insertions(+), 4 deletions(-) diff --git a/lldb/include/lldb/API/SBCommandInterpreter.h b/lldb/include/lldb/API/SBCommandInterpreter.h index ba2e049204b8e..d65f06d676f91 100644 --- a/lldb/include/lldb/API/SBCommandInterpreter.h +++ b/lldb/include/lldb/API/SBCommandInterpreter.h @@ -247,13 +247,13 @@ class SBCommandInterpreter { lldb::SBStringList &matches, lldb::SBStringList &descriptions); - /// Returns whether an interrupt flag was raised either by the SBDebugger - + /// Returns whether an interrupt flag was raised either by the SBDebugger - /// when the function is not running on the RunCommandInterpreter thread, or /// by SBCommandInterpreter::InterruptCommand if it is. If your code is doing - /// interruptible work, check this API periodically, and interrupt if it + /// interruptible work, check this API periodically, and interrupt if it /// returns true. bool WasInterrupted() const; - + /// Interrupts the command currently executing in the RunCommandInterpreter /// thread. /// @@ -318,6 +318,12 @@ class SBCommandInterpreter { SBStructuredData GetStatistics(); + /// Returns a list of handled commands, output and error. Each element in + /// the list is a dictionary with three keys: "command" (string), "output" + /// (list of strings) and optionally "error" (list of strings). Each string + /// in "output" and "error" is a line (without EOL characteres). + SBStructuredData GetTranscript(); + protected: friend class lldb_private::CommandPluginInterfaceImplementation; diff --git a/lldb/source/API/SBCommandInterpreter.cpp b/lldb/source/API/SBCommandInterpreter.cpp index 83c0951c56db6..242b3f8f09c48 100644 --- a/lldb/source/API/SBCommandInterpreter.cpp +++ b/lldb/source/API/SBCommandInterpreter.cpp @@ -150,7 +150,7 @@ bool SBCommandInterpreter::WasInterrupted() const { bool SBCommandInterpreter::InterruptCommand() { LLDB_INSTRUMENT_VA(this); - + return (IsValid() ? m_opaque_ptr->InterruptCommand() : false); } @@ -571,6 +571,11 @@ SBStructuredData SBCommandInterpreter::GetStatistics() { return data; } +SBStructuredData SBCommandInterpreter::GetTranscript() { + LLDB_INSTRUMENT_VA(this); + return SBStructuredData(); +} + lldb::SBCommand SBCommandInterpreter::AddMultiwordCommand(const char *name, const char *help) { LLDB_INSTRUMENT_VA(this, name, help); >From a1c948ceabaccdc3407e0c4eae0ebc594a9b68b7 Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Wed, 1 May 2024 13:45:47 -0700 Subject: [PATCH 02/19] Implement the new API --- .../lldb/Interpreter/CommandInterpreter.h | 12 +-- lldb/include/lldb/Utility/StructuredData.h| 11 +++--- lldb/source/API/SBCommandInterpreter.cpp | 8 - .../source/Interpreter/CommandInterpreter.cpp | 21 ++- lldb/source/Utility/StructuredData.cpp| 35 +++ 5 files changed, 79 insertions(+), 8 deletions(-) diff --git a/lldb/include/lldb/Interpreter/CommandInterpreter.h b/lldb/include/lldb/Interpreter/CommandInterpreter.h index 70a55a77465bf..9474c41c0dced 100644 --- a/lldb/include/lldb/Interpreter/CommandInterpreter.h +++ b/lldb/include/lldb/Interpreter/CommandInterpreter.h @@ -22,6 +22,7 @@ #include "lldb/Utility/Log.h" #include "lldb/Utility/StreamString.h" #include "lldb/Utility/StringList.h" +#include "lldb/Utility/StructuredData.h" #include "lldb/lldb-forward.h" #include "lldb/lldb-private.h" @@ -241,7 +242,7 @@ class CommandInterpreter : public Broadcaster, eCommandTypesAllThem = 0x //< all commands }; - // The CommandAlias and CommandInterpreter both have a hand in + // The CommandAlias and CommandInterpreter both have a hand in // substituting for alias commands. They work by writing special tokens // in the template form of the Alias command, and then detecting them when the // command is executed. These are the special tokens: @@ -576,7 +577,7 @@ class CommandInterpreter : public Broadcaster, void SetEchoCommentCommands(bool enable); bool GetRepeatPreviousCommand() const; - + bool GetRequireCommandOverwrite() const; const CommandObject::CommandMap &GetUserCommands() const { @@ -647,6 +648,7 @@ class CommandInterpreter : public Broadcaster, } llvm::json::Value GetStatistics(); + StructuredData::ArraySP GetTranscript() const; protected: friend class Debugger; @@ -766,6 +768,12 @@ class CommandInterpreter : public Broadcaster
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
https://github.com/clayborg approved this pull request. https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
https://github.com/royitaqi updated https://github.com/llvm/llvm-project/pull/89868 >From 079a550481d4cdcb69ad01c376b5e1f0632a07d6 Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Tue, 23 Apr 2024 18:10:21 -0700 Subject: [PATCH 01/19] Allow multiple destroy callbacks in `SBDebugger::SetDestroyCallback()` --- lldb/include/lldb/Core/Debugger.h | 4 ++-- lldb/source/Core/Debugger.cpp | 10 +- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index 418c2403d020f..20884f954ec7d 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -731,8 +731,8 @@ class Debugger : public std::enable_shared_from_this, lldb::TargetSP m_dummy_target_sp; Diagnostics::CallbackID m_diagnostics_callback_id; - lldb_private::DebuggerDestroyCallback m_destroy_callback = nullptr; - void *m_destroy_callback_baton = nullptr; + std::vector> + m_destroy_callback_and_baton; uint32_t m_interrupt_requested = 0; ///< Tracks interrupt requests std::mutex m_interrupt_mutex; diff --git a/lldb/source/Core/Debugger.cpp b/lldb/source/Core/Debugger.cpp index 19b3cf3bbf46b..0ebdf2b0a0f97 100644 --- a/lldb/source/Core/Debugger.cpp +++ b/lldb/source/Core/Debugger.cpp @@ -743,10 +743,11 @@ DebuggerSP Debugger::CreateInstance(lldb::LogOutputCallback log_callback, } void Debugger::HandleDestroyCallback() { - if (m_destroy_callback) { -m_destroy_callback(GetID(), m_destroy_callback_baton); -m_destroy_callback = nullptr; + const lldb::user_id_t user_id = GetID(); + for (const auto &callback_and_baton : m_destroy_callback_and_baton) { +callback_and_baton.first(user_id, callback_and_baton.second); } + m_destroy_callback_and_baton.clear(); } void Debugger::Destroy(DebuggerSP &debugger_sp) { @@ -1427,8 +1428,7 @@ void Debugger::SetLoggingCallback(lldb::LogOutputCallback log_callback, void Debugger::SetDestroyCallback( lldb_private::DebuggerDestroyCallback destroy_callback, void *baton) { - m_destroy_callback = destroy_callback; - m_destroy_callback_baton = baton; + m_destroy_callback_and_baton.emplace_back(destroy_callback, baton); } static void PrivateReportProgress(Debugger &debugger, uint64_t progress_id, >From 771b52723be8d0ffecaf8f0818105cfdb82ba332 Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Tue, 23 Apr 2024 21:05:58 -0700 Subject: [PATCH 02/19] Fix code format --- lldb/include/lldb/Core/Debugger.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index 20884f954ec7d..af025219b0bc1 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -732,7 +732,7 @@ class Debugger : public std::enable_shared_from_this, Diagnostics::CallbackID m_diagnostics_callback_id; std::vector> - m_destroy_callback_and_baton; + m_destroy_callback_and_baton; uint32_t m_interrupt_requested = 0; ///< Tracks interrupt requests std::mutex m_interrupt_mutex; >From d1f13cad8a3789a994572459893b32a225ba3e1b Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Wed, 24 Apr 2024 11:55:16 -0700 Subject: [PATCH 03/19] Add `AddDestroyCallback()` and `ClearDestroyCallback()` --- lldb/include/lldb/Core/Debugger.h | 11 +++ lldb/source/Core/Debugger.cpp | 12 +++- 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index af025219b0bc1..5b3e433f09c68 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -568,10 +568,21 @@ class Debugger : public std::enable_shared_from_this, static void ReportSymbolChange(const ModuleSpec &module_spec); + /// Add a callback for when the debugger is destroyed. A list is maintained + /// internally. + void + AddDestroyCallback(lldb_private::DebuggerDestroyCallback destroy_callback, + void *baton); + + /// Clear the list of callbacks, then add the callback. void SetDestroyCallback(lldb_private::DebuggerDestroyCallback destroy_callback, void *baton); + /// Clear the list of callbacks. + void + ClearDestroyCallback(); + /// Manually start the global event handler thread. It is useful to plugins /// that directly use the \a lldb_private namespace and want to use the /// debugger's default event handler thread instead of defining their own. diff --git a/lldb/source/Core/Debugger.cpp b/lldb/source/Core/Debugger.cpp index 0ebdf2b0a0f97..159913642f253 100644 --- a/lldb/source/Core/Debugger.cpp +++ b/lldb/source/Core/Debugger.cpp @@ -1426,11 +1426,21 @@ void Debugger::SetLoggingCallback(lldb::LogOutputCallback log_callback, std::make_shared(log_callback, baton); } -void Debugger::SetDestroyCallback( +void Debugger::AddDestroyCallback( lldb_private::DebuggerDestroyCallback destroy_callback, void *b
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
https://github.com/clayborg approved this pull request. Thanks for all of the changes. Looks good. https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
@@ -731,8 +747,12 @@ class Debugger : public std::enable_shared_from_this, lldb::TargetSP m_dummy_target_sp; Diagnostics::CallbackID m_diagnostics_callback_id; - lldb_private::DebuggerDestroyCallback m_destroy_callback = nullptr; - void *m_destroy_callback_baton = nullptr; + std::mutex m_destroy_callback_mutex; + lldb::destroy_callback_token_t m_destroy_callback_next_token = 0; + typedef std::tuple royitaqi wrote: Added. FWIW, I had to add two ctors: - Default ctor for `DestroyCallbackInfo callback_info;`, used in `HandleDestroyCallback()`. - A ctor which assigns 3 members for `m_destroy_callbacks.emplace_back(token, destroy_callback, baton);`, used in `AddDestroyCallback()`. https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
https://github.com/royitaqi updated https://github.com/llvm/llvm-project/pull/90703 >From 323b882db7f2845563176ca057c9cd2c88f3492a Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Tue, 30 Apr 2024 21:35:49 -0700 Subject: [PATCH 01/19] Add SBCommandInterpreter::GetTranscript() --- lldb/include/lldb/API/SBCommandInterpreter.h | 12 +--- lldb/source/API/SBCommandInterpreter.cpp | 7 ++- 2 files changed, 15 insertions(+), 4 deletions(-) diff --git a/lldb/include/lldb/API/SBCommandInterpreter.h b/lldb/include/lldb/API/SBCommandInterpreter.h index ba2e049204b8e..d65f06d676f91 100644 --- a/lldb/include/lldb/API/SBCommandInterpreter.h +++ b/lldb/include/lldb/API/SBCommandInterpreter.h @@ -247,13 +247,13 @@ class SBCommandInterpreter { lldb::SBStringList &matches, lldb::SBStringList &descriptions); - /// Returns whether an interrupt flag was raised either by the SBDebugger - + /// Returns whether an interrupt flag was raised either by the SBDebugger - /// when the function is not running on the RunCommandInterpreter thread, or /// by SBCommandInterpreter::InterruptCommand if it is. If your code is doing - /// interruptible work, check this API periodically, and interrupt if it + /// interruptible work, check this API periodically, and interrupt if it /// returns true. bool WasInterrupted() const; - + /// Interrupts the command currently executing in the RunCommandInterpreter /// thread. /// @@ -318,6 +318,12 @@ class SBCommandInterpreter { SBStructuredData GetStatistics(); + /// Returns a list of handled commands, output and error. Each element in + /// the list is a dictionary with three keys: "command" (string), "output" + /// (list of strings) and optionally "error" (list of strings). Each string + /// in "output" and "error" is a line (without EOL characteres). + SBStructuredData GetTranscript(); + protected: friend class lldb_private::CommandPluginInterfaceImplementation; diff --git a/lldb/source/API/SBCommandInterpreter.cpp b/lldb/source/API/SBCommandInterpreter.cpp index 83c0951c56db6..242b3f8f09c48 100644 --- a/lldb/source/API/SBCommandInterpreter.cpp +++ b/lldb/source/API/SBCommandInterpreter.cpp @@ -150,7 +150,7 @@ bool SBCommandInterpreter::WasInterrupted() const { bool SBCommandInterpreter::InterruptCommand() { LLDB_INSTRUMENT_VA(this); - + return (IsValid() ? m_opaque_ptr->InterruptCommand() : false); } @@ -571,6 +571,11 @@ SBStructuredData SBCommandInterpreter::GetStatistics() { return data; } +SBStructuredData SBCommandInterpreter::GetTranscript() { + LLDB_INSTRUMENT_VA(this); + return SBStructuredData(); +} + lldb::SBCommand SBCommandInterpreter::AddMultiwordCommand(const char *name, const char *help) { LLDB_INSTRUMENT_VA(this, name, help); >From 5c4f7ce757d63b2d41b138775a9f7b061fc4a2ef Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Wed, 1 May 2024 13:45:47 -0700 Subject: [PATCH 02/19] Implement the new API --- .../lldb/Interpreter/CommandInterpreter.h | 12 +-- lldb/include/lldb/Utility/StructuredData.h| 11 +++--- lldb/source/API/SBCommandInterpreter.cpp | 8 - .../source/Interpreter/CommandInterpreter.cpp | 21 ++- lldb/source/Utility/StructuredData.cpp| 35 +++ 5 files changed, 79 insertions(+), 8 deletions(-) diff --git a/lldb/include/lldb/Interpreter/CommandInterpreter.h b/lldb/include/lldb/Interpreter/CommandInterpreter.h index 70a55a77465bf..9474c41c0dced 100644 --- a/lldb/include/lldb/Interpreter/CommandInterpreter.h +++ b/lldb/include/lldb/Interpreter/CommandInterpreter.h @@ -22,6 +22,7 @@ #include "lldb/Utility/Log.h" #include "lldb/Utility/StreamString.h" #include "lldb/Utility/StringList.h" +#include "lldb/Utility/StructuredData.h" #include "lldb/lldb-forward.h" #include "lldb/lldb-private.h" @@ -241,7 +242,7 @@ class CommandInterpreter : public Broadcaster, eCommandTypesAllThem = 0x //< all commands }; - // The CommandAlias and CommandInterpreter both have a hand in + // The CommandAlias and CommandInterpreter both have a hand in // substituting for alias commands. They work by writing special tokens // in the template form of the Alias command, and then detecting them when the // command is executed. These are the special tokens: @@ -576,7 +577,7 @@ class CommandInterpreter : public Broadcaster, void SetEchoCommentCommands(bool enable); bool GetRepeatPreviousCommand() const; - + bool GetRequireCommandOverwrite() const; const CommandObject::CommandMap &GetUserCommands() const { @@ -647,6 +648,7 @@ class CommandInterpreter : public Broadcaster, } llvm::json::Value GetStatistics(); + StructuredData::ArraySP GetTranscript() const; protected: friend class Debugger; @@ -766,6 +768,12 @@ class CommandInterpreter : public Broadcaster
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
https://github.com/royitaqi updated https://github.com/llvm/llvm-project/pull/89868 >From 079a550481d4cdcb69ad01c376b5e1f0632a07d6 Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Tue, 23 Apr 2024 18:10:21 -0700 Subject: [PATCH 01/19] Allow multiple destroy callbacks in `SBDebugger::SetDestroyCallback()` --- lldb/include/lldb/Core/Debugger.h | 4 ++-- lldb/source/Core/Debugger.cpp | 10 +- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index 418c2403d020f..20884f954ec7d 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -731,8 +731,8 @@ class Debugger : public std::enable_shared_from_this, lldb::TargetSP m_dummy_target_sp; Diagnostics::CallbackID m_diagnostics_callback_id; - lldb_private::DebuggerDestroyCallback m_destroy_callback = nullptr; - void *m_destroy_callback_baton = nullptr; + std::vector> + m_destroy_callback_and_baton; uint32_t m_interrupt_requested = 0; ///< Tracks interrupt requests std::mutex m_interrupt_mutex; diff --git a/lldb/source/Core/Debugger.cpp b/lldb/source/Core/Debugger.cpp index 19b3cf3bbf46b..0ebdf2b0a0f97 100644 --- a/lldb/source/Core/Debugger.cpp +++ b/lldb/source/Core/Debugger.cpp @@ -743,10 +743,11 @@ DebuggerSP Debugger::CreateInstance(lldb::LogOutputCallback log_callback, } void Debugger::HandleDestroyCallback() { - if (m_destroy_callback) { -m_destroy_callback(GetID(), m_destroy_callback_baton); -m_destroy_callback = nullptr; + const lldb::user_id_t user_id = GetID(); + for (const auto &callback_and_baton : m_destroy_callback_and_baton) { +callback_and_baton.first(user_id, callback_and_baton.second); } + m_destroy_callback_and_baton.clear(); } void Debugger::Destroy(DebuggerSP &debugger_sp) { @@ -1427,8 +1428,7 @@ void Debugger::SetLoggingCallback(lldb::LogOutputCallback log_callback, void Debugger::SetDestroyCallback( lldb_private::DebuggerDestroyCallback destroy_callback, void *baton) { - m_destroy_callback = destroy_callback; - m_destroy_callback_baton = baton; + m_destroy_callback_and_baton.emplace_back(destroy_callback, baton); } static void PrivateReportProgress(Debugger &debugger, uint64_t progress_id, >From 771b52723be8d0ffecaf8f0818105cfdb82ba332 Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Tue, 23 Apr 2024 21:05:58 -0700 Subject: [PATCH 02/19] Fix code format --- lldb/include/lldb/Core/Debugger.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index 20884f954ec7d..af025219b0bc1 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -732,7 +732,7 @@ class Debugger : public std::enable_shared_from_this, Diagnostics::CallbackID m_diagnostics_callback_id; std::vector> - m_destroy_callback_and_baton; + m_destroy_callback_and_baton; uint32_t m_interrupt_requested = 0; ///< Tracks interrupt requests std::mutex m_interrupt_mutex; >From d1f13cad8a3789a994572459893b32a225ba3e1b Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Wed, 24 Apr 2024 11:55:16 -0700 Subject: [PATCH 03/19] Add `AddDestroyCallback()` and `ClearDestroyCallback()` --- lldb/include/lldb/Core/Debugger.h | 11 +++ lldb/source/Core/Debugger.cpp | 12 +++- 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index af025219b0bc1..5b3e433f09c68 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -568,10 +568,21 @@ class Debugger : public std::enable_shared_from_this, static void ReportSymbolChange(const ModuleSpec &module_spec); + /// Add a callback for when the debugger is destroyed. A list is maintained + /// internally. + void + AddDestroyCallback(lldb_private::DebuggerDestroyCallback destroy_callback, + void *baton); + + /// Clear the list of callbacks, then add the callback. void SetDestroyCallback(lldb_private::DebuggerDestroyCallback destroy_callback, void *baton); + /// Clear the list of callbacks. + void + ClearDestroyCallback(); + /// Manually start the global event handler thread. It is useful to plugins /// that directly use the \a lldb_private namespace and want to use the /// debugger's default event handler thread instead of defining their own. diff --git a/lldb/source/Core/Debugger.cpp b/lldb/source/Core/Debugger.cpp index 0ebdf2b0a0f97..159913642f253 100644 --- a/lldb/source/Core/Debugger.cpp +++ b/lldb/source/Core/Debugger.cpp @@ -1426,11 +1426,21 @@ void Debugger::SetLoggingCallback(lldb::LogOutputCallback log_callback, std::make_shared(log_callback, baton); } -void Debugger::SetDestroyCallback( +void Debugger::AddDestroyCallback( lldb_private::DebuggerDestroyCallback destroy_callback, void *b
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
https://github.com/clayborg requested changes to this pull request. See inlined comments as the `SBAddressRange::GetDescription()` could have crashed if we had an address with a no section and we did supply a valid target. So changes needed: - add a test for a SBAddressRange object that is constructed with a SBAddress that has no section, just a raw address, and we print it out with a valid target (which won't be used because there is no section to resolve) - change address ranges to be emitted as `[, )` (end the range with a `)` instead of a `]` to indicate the range is not inclusive (for both the case where we have a module name and/or just dumping a load address range or file address range - make sure an address range that has a valid section, but that section isn't loaded into the target yet that your test can dump it before your run your debug program and see `a.out[0x1000-0x2000)`, and then test once it is running and stopped and the section is loaded and it will print out using the `[, )` https://github.com/llvm/llvm-project/pull/92014 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
@@ -203,3 +208,38 @@ void AddressRange::DumpDebug(Stream *s) const { static_cast(m_base_addr.GetSection().get()), m_base_addr.GetOffset(), GetByteSize()); } + +bool AddressRange::GetDescription(Stream *s, Target *target) const { + const char *file_name = nullptr; + addr_t start_addr = LLDB_INVALID_ADDRESS; + + if (target == nullptr) { +const auto section_sp = m_base_addr.GetSection(); +if (section_sp) { + const auto object_file = section_sp->GetObjectFile(); + if (object_file != nullptr) +file_name = object_file->GetFileSpec().GetFilename().AsCString(); +} +start_addr = m_base_addr.GetFileAddress(); + } else { +start_addr = m_base_addr.GetLoadAddress(target); +file_name = ""; + } + + const addr_t end_addr = (start_addr == LLDB_INVALID_ADDRESS) + ? LLDB_INVALID_ADDRESS + : start_addr + GetByteSize(); clayborg wrote: This might be easier to read and reason with if we structure it like: ``` addr_t start_addr = m_base_addr.GetLoadAddress(target); if (start_addr != LLDB_INVALID_ADDRESS) { // We have a valid target and the address was resolved, or we have a base address // with no section. Just print out a raw address range: [, ) s->Printf("[0x%" PRIx64 "-0x%" PRIx64 ")", start_addr, start_addr + GetByteSize()); return; } // Either no target or the address wasn't resolved, print as [-) const char *file_name = ""; const auto section_sp = m_base_addr.GetSection(); if (section_sp) { if (const auto object_file = section_sp->GetObjectFile()) file_name = object_file->GetFileSpec().GetFilename().AsCString(); } start_addr = m_base_addr.GetFileAddress(); const addr_t end_addr = (start_addr == LLDB_INVALID_ADDRESS) ? LLDB_INVALID_ADDRESS : start_addr + GetByteSize(); s->Printf("%s[0x%" PRIx64 "-0x%" PRIx64 "]", file_name, start_addr, end_addr); ``` the above `m_base_addr.GetLoadAddress(target)` call knows to check for a NULL target and will return LLDB_INVALID_ADDRESS if that is the case and there is a section. https://github.com/llvm/llvm-project/pull/92014 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
@@ -203,3 +208,38 @@ void AddressRange::DumpDebug(Stream *s) const { static_cast(m_base_addr.GetSection().get()), m_base_addr.GetOffset(), GetByteSize()); } + +bool AddressRange::GetDescription(Stream *s, Target *target) const { + const char *file_name = nullptr; + addr_t start_addr = LLDB_INVALID_ADDRESS; + + if (target == nullptr) { +const auto section_sp = m_base_addr.GetSection(); +if (section_sp) { + const auto object_file = section_sp->GetObjectFile(); + if (object_file != nullptr) +file_name = object_file->GetFileSpec().GetFilename().AsCString(); +} +start_addr = m_base_addr.GetFileAddress(); + } else { +start_addr = m_base_addr.GetLoadAddress(target); +file_name = ""; + } + + const addr_t end_addr = (start_addr == LLDB_INVALID_ADDRESS) + ? LLDB_INVALID_ADDRESS + : start_addr + GetByteSize(); + s->Printf("%s[0x%" PRIx64 "-0x%" PRIx64 "]", file_name, start_addr, end_addr); clayborg wrote: The end address isn't inclusive, so this should be: ``` s->Printf("%s[0x%" PRIx64 "-0x%" PRIx64 ")", file_name, start_addr, end_addr); ``` (change the closing brace from a `]` to a `)`) https://github.com/llvm/llvm-project/pull/92014 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
@@ -0,0 +1,216 @@ +""" +Test SBAddressRange APIs. +""" + +import lldb +from lldbsuite.test.lldbtest import * + + +class AddressRangeTestCase(TestBase): +NO_DEBUG_INFO_TESTCASE = True + +def setUp(self): +TestBase.setUp(self) + +self.build() +exe = self.getBuildArtifact("a.out") + +self.dbg.SetAsync(True) + +self.target = self.dbg.CreateTarget(exe) +self.assertTrue(self.target, VALID_TARGET) +self.launch_info = self.target.GetLaunchInfo() + self.launch_info.SetWorkingDirectory(self.get_process_working_directory()) + +self.bp1 = self.target.BreakpointCreateByName("main", "a.out") +self.bp2 = self.target.BreakpointCreateByName("foo", "a.out") +self.bp3 = self.target.BreakpointCreateByName("bar", "a.out") + +self.assertTrue(self.bp1.IsValid()) +self.assertTrue(self.bp2.IsValid()) +self.assertTrue(self.bp3.IsValid()) + +self.addr1 = self.bp1.GetLocationAtIndex(0).GetAddress() +self.addr2 = self.bp2.GetLocationAtIndex(0).GetAddress() +self.addr3 = self.bp3.GetLocationAtIndex(0).GetAddress() + +self.assertTrue(self.addr1.IsValid()) +self.assertTrue(self.addr2.IsValid()) +self.assertTrue(self.addr3.IsValid()) + +def test_address_range_default(self): +"""Testing default constructor.""" +empty_range = lldb.SBAddressRange() +self.assertEqual(empty_range.IsValid(), False) + +def test_address_range_construction(self): +"""Make sure the construction and getters work.""" +range = lldb.SBAddressRange(self.addr1, 8) +self.assertEqual(range.IsValid(), True) +self.assertEqual(range.GetBaseAddress(), self.addr1) +self.assertEqual(range.GetByteSize(), 8) + +def test_address_range_clear(self): +"""Make sure the clear method works.""" +range = lldb.SBAddressRange(self.addr1, 8) +self.assertEqual(range.IsValid(), True) +self.assertEqual(range.GetBaseAddress(), self.addr1) +self.assertEqual(range.GetByteSize(), 8) + +range.Clear() +self.assertEqual(range.IsValid(), False) + +def test_function(self): +"""Make sure the range works in SBFunction APIs.""" + +# Setup breakpoints in main +loc = self.bp1.GetLocationAtIndex(0) +loc_addr = loc.GetAddress() +func = loc_addr.GetFunction() +ranges = func.GetRanges() +self.assertEqual(ranges.GetSize(), 1) + +range = ranges.GetAddressRangeAtIndex(0) +self.assertEqual( +range.GetByteSize(), +func.GetEndAddress().GetOffset() - func.GetStartAddress().GetOffset(), +) +self.assertEqual( +range.GetBaseAddress().GetOffset(), +func.GetStartAddress().GetOffset(), +) + +def test_block(self): +"""Make sure the range works in SBBlock APIs.""" +loc = self.bp1.GetLocationAtIndex(0) +loc_addr = loc.GetAddress() +block = loc_addr.GetBlock() + +ranges = block.GetRanges() +self.assertEqual(ranges.GetSize(), 1) + +range = ranges.GetAddressRangeAtIndex(0) +self.assertEqual( +range.GetByteSize(), +block.GetRangeEndAddress(0).GetOffset() +- block.GetRangeStartAddress(0).GetOffset(), +) +self.assertEqual( +range.GetBaseAddress().GetOffset(), +block.GetRangeStartAddress(0).GetOffset(), +) + +def test_address_range_list(self): +"""Make sure the SBAddressRangeList works by adding and getting ranges.""" +range1 = lldb.SBAddressRange(self.addr1, 8) +range2 = lldb.SBAddressRange(self.addr2, 16) +range3 = lldb.SBAddressRange(self.addr3, 32) + +range_list = lldb.SBAddressRangeList() +self.assertEqual(range_list.GetSize(), 0) + +range_list.Append(range1) +range_list.Append(range2) +range_list.Append(range3) +self.assertEqual(range_list.GetSize(), 3) +self.assertRaises(IndexError, lambda: range_list[3]) + +range1_copy = range_list.GetAddressRangeAtIndex(0) +self.assertEqual(range1.GetByteSize(), range1_copy.GetByteSize()) +self.assertEqual( +range1.GetBaseAddress().GetOffset(), +range1_copy.GetBaseAddress().GetOffset(), +) + +range2_copy = range_list.GetAddressRangeAtIndex(1) +self.assertEqual(range2.GetByteSize(), range2_copy.GetByteSize()) +self.assertEqual( +range2.GetBaseAddress().GetOffset(), +range2_copy.GetBaseAddress().GetOffset(), +) + +range3_copy = range_list.GetAddressRangeAtIndex(2) +self.assertEqual(range3.GetByteSize(), range3_copy.GetByteSize()) +self.assertEqual( +range3.GetBaseAddress().GetOffset(), +range3_copy.GetBaseAddress().GetOffset(), +) +
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
@@ -203,3 +208,38 @@ void AddressRange::DumpDebug(Stream *s) const { static_cast(m_base_addr.GetSection().get()), m_base_addr.GetOffset(), GetByteSize()); } + +bool AddressRange::GetDescription(Stream *s, Target *target) const { + const char *file_name = nullptr; clayborg wrote: Init this with "" so we don't need to set it. We need to do this because a valid target can be supplied, but it might not have the section loaded yet. But we can also have a AddressRange with no section, and below on line 221, we only set the filename to valid if there is a section, so this code can crash if we have a target but no section as file_name will be NULL and crash in the `Printf(...)` call below. https://github.com/llvm/llvm-project/pull/92014 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
https://github.com/clayborg edited https://github.com/llvm/llvm-project/pull/92014 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add AddressRange to SB API (PR #92014)
@@ -0,0 +1,65 @@ +//===-- SBAddressRange.h *- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===--===// + +#ifndef LLDB_API_SBADDRESSRANGE_H +#define LLDB_API_SBADDRESSRANGE_H + +#include "lldb/API/SBDefines.h" + +namespace lldb { + +class LLDB_API SBAddressRange { +public: + SBAddressRange(); + + SBAddressRange(const lldb::SBAddressRange &rhs); + + SBAddressRange(lldb::SBAddress addr, lldb::addr_t byte_size); + + ~SBAddressRange(); + + const lldb::SBAddressRange &operator=(const lldb::SBAddressRange &rhs); + + void Clear(); + + /// Check the address range refers to a valid base address and has a byte + /// size greater than zero. + /// + /// \return + /// True if the address range is valid, false otherwise. + bool IsValid() const; + + /// Get the base address of the range. + /// + /// \return + /// Base address object. + lldb::SBAddress GetBaseAddress() const; + + /// Get the byte size of this range. + /// + /// \return + /// The size in bytes of this address range. + lldb::addr_t GetByteSize() const; + + bool operator==(const SBAddressRange &rhs); + + bool operator!=(const SBAddressRange &rhs); + + bool GetDescription(lldb::SBStream &description, SBTarget *target); clayborg wrote: We don't pass pointers to SB objects in our current API. Can this be changed from `SBTarget *target` to `SBTarget &target`? Or will that make the `lldb.target` stuff not work in the python layer? Either way this should be changed to use `SBTarget &`. If we need to work around this in the python extension code, then we might need to versions of this function: one with a `SBTarget &target` and one without. Then the python can do a: ``` def __repr__(self): import lldb stream = lldb.SBStream() if lldb.target is None: self.GetDescription(stream) else: self.GetDescription(stream, lldb.target) return stream.GetData() ``` We might want to clarify why we have the target parameter here in headerdoc like: ``` /// Dump the contents of this SBAddressRange object. /// /// \param[in] strm ///The stream to dump the contents to. /// /// \param[in] target ///The target to use to resolve the SBAddress base address. If an invalid target ///is passed in, or if the base address isn't loaded in the target yet the address ///range will be shown as the module name followed by a file address range: ///a.out[0x1000-0x02000). If a valid target is supplied and the section is loaded ///then the address range will be dumped as a load address range: [0x101000-0x102000) /// /// \return /// . ``` Where `...` above will be an explanation of how the address is displayed without being able to resolve the base address `a.out[0x1000-0x2000)`) https://github.com/llvm/llvm-project/pull/92014 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
github-actions[bot] wrote: :warning: Python code formatter, darker found issues in your code. :warning: You can test this locally with the following command: ``bash darker --check --diff -r 7ecdf620330d8e044a48b6f59f8eddd2f88f01d4...25a51ed4e87042411b03ba4e57cb4a595679c37b lldb/test/API/python_api/debugger/TestDebuggerAPI.py `` View the diff from darker here. ``diff --- TestDebuggerAPI.py 2024-05-17 00:49:05.00 + +++ TestDebuggerAPI.py 2024-05-20 22:39:20.840610 + @@ -167,69 +167,72 @@ called = [] def foo(dbg_id): # Need nonlocal to modify closure variable. nonlocal called -called += [('foo', dbg_id)] +called += [("foo", dbg_id)] def bar(dbg_id): # Need nonlocal to modify closure variable. nonlocal called -called += [('bar', dbg_id)] +called += [("bar", dbg_id)] token_foo = self.dbg.AddDestroyCallback(foo) token_bar = self.dbg.AddDestroyCallback(bar) self.dbg.Destroy(self.dbg) # Should call both `foo()` and `bar()`. -self.assertEqual(called, [ -('foo', original_dbg_id), -('bar', original_dbg_id), -]) +self.assertEqual( +called, +[ +("foo", original_dbg_id), +("bar", original_dbg_id), +], +) def test_RemoveDestroyCallback(self): original_dbg_id = self.dbg.GetID() called = [] def foo(dbg_id): # Need nonlocal to modify closure variable. nonlocal called -called += [('foo', dbg_id)] +called += [("foo", dbg_id)] def bar(dbg_id): # Need nonlocal to modify closure variable. nonlocal called -called += [('bar', dbg_id)] +called += [("bar", dbg_id)] token_foo = self.dbg.AddDestroyCallback(foo) token_bar = self.dbg.AddDestroyCallback(bar) ret = self.dbg.RemoveDestroyCallback(token_foo) self.dbg.Destroy(self.dbg) # `Remove` should be successful self.assertTrue(ret) # Should only call `bar()` -self.assertEqual(called, [('bar', original_dbg_id)]) +self.assertEqual(called, [("bar", original_dbg_id)]) def test_RemoveDestroyCallback_invalid_token(self): original_dbg_id = self.dbg.GetID() magic_token_that_should_not_exist = 32413 called = [] def foo(dbg_id): # Need nonlocal to modify closure variable. nonlocal called -called += [('foo', dbg_id)] +called += [("foo", dbg_id)] token_foo = self.dbg.AddDestroyCallback(foo) ret = self.dbg.RemoveDestroyCallback(magic_token_that_should_not_exist) self.dbg.Destroy(self.dbg) # `Remove` should be unsuccessful self.assertFalse(ret) # Should call `foo()` -self.assertEqual(called, [('foo', original_dbg_id)]) +self.assertEqual(called, [("foo", original_dbg_id)]) def test_HandleDestroyCallback(self): """ Validates: 1. AddDestroyCallback and RemoveDestroyCallback work during debugger destroy. @@ -240,45 +243,51 @@ bar_token = None def foo(dbg_id): # Need nonlocal to modify closure variable. nonlocal events -events.append(('foo called', dbg_id)) +events.append(("foo called", dbg_id)) def bar(dbg_id): # Need nonlocal to modify closure variable. nonlocal events -events.append(('bar called', dbg_id)) +events.append(("bar called", dbg_id)) def add_foo(dbg_id): # Need nonlocal to modify closure variable. nonlocal events -events.append(('add_foo called', dbg_id)) -events.append(('foo token', self.dbg.AddDestroyCallback(foo))) +events.append(("add_foo called", dbg_id)) +events.append(("foo token", self.dbg.AddDestroyCallback(foo))) def remove_bar(dbg_id): # Need nonlocal to modify closure variable. nonlocal events -events.append(('remove_bar called', dbg_id)) -events.append(('remove bar ret', self.dbg.RemoveDestroyCallback(bar_token))) +events.append(("remove_bar called", dbg_id)) +events.append(("remove bar ret", self.dbg.RemoveDestroyCallback(bar_token))) # Setup -events.append(('add_foo token', self.dbg.AddDestroyCallback(add_foo))) +events.append(("add_foo token", self.dbg.AddDestroyCallback(add_foo))) bar_token = self.dbg.AddDestroyCallback(bar) -events.append(('bar token', bar_token)) -events.append(('remove_bar token', self.dbg.AddDestroyCallback(remove_bar))) +eve
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
github-actions[bot] wrote: :warning: Python code formatter, darker found issues in your code. :warning: You can test this locally with the following command: ``bash darker --check --diff -r 7ecdf620330d8e044a48b6f59f8eddd2f88f01d4...542615a18949f6f325c03761104b2f0530270065 lldb/test/API/commands/session/save/TestSessionSave.py lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py `` View the diff from darker here. ``diff --- python_api/interpreter/TestCommandInterpreterAPI.py 2024-05-20 22:05:58.00 + +++ python_api/interpreter/TestCommandInterpreterAPI.py 2024-05-20 22:39:44.633426 + @@ -140,27 +140,31 @@ # 1. Some of the asserts rely on the exact output format of the #commands. Hopefully we are not changing them any time soon. # 2. We are removing the "seconds" field from each command, so that #some of the validations below can be easier / more readable. for command in transcript: -del(command["seconds"]) +del command["seconds"] # (lldb) version self.assertEqual(transcript[0]["command"], "version") self.assertIn("lldb version", transcript[0]["output"]) self.assertEqual(transcript[0]["error"], "") # (lldb) an-unknown-command -self.assertEqual(transcript[1], +self.assertEqual( +transcript[1], { "command": "an-unknown-command", "output": "", "error": "error: 'an-unknown-command' is not a valid command.\n", -}) +}, +) # (lldb) breakpoint set -f main.c -l -self.assertEqual(transcript[2]["command"], "breakpoint set -f main.c -l %d" % self.line) +self.assertEqual( +transcript[2]["command"], "breakpoint set -f main.c -l %d" % self.line +) # Breakpoint 1: where = a.out`main + 29 at main.c:5:3, address = 0x00010f7d self.assertIn("Breakpoint 1: where = a.out`main ", transcript[2]["output"]) self.assertEqual(transcript[2]["error"], "") # (lldb) r @@ -169,16 +173,18 @@ self.assertIn("Process", transcript[3]["output"]) self.assertIn("launched", transcript[3]["output"]) self.assertEqual(transcript[3]["error"], "") # (lldb) p a -self.assertEqual(transcript[4], +self.assertEqual( +transcript[4], { "command": "p a", "output": "(int) 123\n", "error": "", -}) +}, +) # (lldb) statistics dump statistics_dump = json.loads(transcript[5]["output"]) # Dump result should be valid JSON self.assertTrue(statistics_dump is not json.JSONDecodeError) @@ -191,11 +197,14 @@ def test_save_transcript_setting_default(self): ci = self.buildAndCreateTarget() res = lldb.SBCommandReturnObject() # The setting's default value should be "false" -self.runCmd("settings show interpreter.save-transcript", "interpreter.save-transcript (boolean) = false\n") +self.runCmd( +"settings show interpreter.save-transcript", +"interpreter.save-transcript (boolean) = false\n", +) # self.assertEqual(res.GetOutput(), ) def test_save_transcript_setting_off(self): ci = self.buildAndCreateTarget() @@ -237,19 +246,39 @@ # Run commands and get the transcript as structured data self.runCmd("version") structured_data_1 = ci.GetTranscript() self.assertTrue(structured_data_1.IsValid()) self.assertEqual(structured_data_1.GetSize(), 1) - self.assertEqual(structured_data_1.GetItemAtIndex(0).GetValueForKey("command").GetStringValue(100), "version") +self.assertEqual( +structured_data_1.GetItemAtIndex(0) +.GetValueForKey("command") +.GetStringValue(100), +"version", +) # Run some more commands and get the transcript as structured data again self.runCmd("help") structured_data_2 = ci.GetTranscript() self.assertTrue(structured_data_2.IsValid()) self.assertEqual(structured_data_2.GetSize(), 2) - self.assertEqual(structured_data_2.GetItemAtIndex(0).GetValueForKey("command").GetStringValue(100), "version") - self.assertEqual(structured_data_2.GetItemAtIndex(1).GetValueForKey("command").GetStringValue(100), "help") +self.assertEqual( +structured_data_2.GetItemAtIndex(0) +.GetValueForKey("command") +.GetStringValue(100), +"version", +) +self.assertEqual( +structured_data_2.GetItemAtIndex(1) +.GetValueForKey("command") +.GetStringValue(100), +"help", +) # N
[Lldb-commits] [lldb] e8dc8d6 - Add new Python API `SBCommandInterpreter::GetTranscript()` (#90703)
Author: royitaqi Date: 2024-05-20T15:49:46-07:00 New Revision: e8dc8d614ada201e250fbf075241b2b6180943b5 URL: https://github.com/llvm/llvm-project/commit/e8dc8d614ada201e250fbf075241b2b6180943b5 DIFF: https://github.com/llvm/llvm-project/commit/e8dc8d614ada201e250fbf075241b2b6180943b5.diff LOG: Add new Python API `SBCommandInterpreter::GetTranscript()` (#90703) # Motivation Currently, the user can already get the "transcript" (for "what is the transcript", see `CommandInterpreter::SaveTranscript`). However, the only way to obtain the transcript data as a user is to first destroy the debugger, then read the save directory. Note that destroy-callbacks cannot be used, because 1\ transcript data is private to the command interpreter (see `CommandInterpreter.h`), and 2\ the writing of the transcript is *after* the invocation of destory-callbacks (see `Debugger::Destroy`). So basically, there is no way to obtain the transcript: * during the lifetime of a debugger (including the destroy-callbacks, which often performs logging tasks, where the transcript can be useful) * without relying on external storage In theory, there are other ways for user to obtain transcript data during a debugger's life cycle: * Use Python API and intercept commands and results. * Use CLI and record console input/output. However, such ways rely on the client's setup and are not supported natively by LLDB. # Proposal Add a new Python API `SBCommandInterpreter::GetTranscript()`. Goals: * It can be called at any time during the debugger's life cycle, including in destroy-callbacks. * It returns data in-memory. Structured data: * To make data processing easier, the return type is `SBStructuredData`. See comments in code for how the data is organized. * In the future, `SaveTranscript` can be updated to write different formats using such data (e.g. JSON). This is probably accompanied by a new setting (e.g. `interpreter.save-session-format`). # Alternatives The return type can also be `std::vector>`. This will make implementation easier, without having to translate it to `SBStructuredData`. On the other hand, `SBStructuredData` can convert to JSON easily, so it's more convenient for user to process. # Privacy Both user commands and output/error in the transcript can contain privacy data. However, as mentioned, the transcript is already available to the user. The addition of the new API doesn't increase the level of risk. In fact, it _lowers_ the risk of privacy data being leaked later on, by avoiding writing such data to external storage. Once the user (or their code) gets the transcript, it will be their responsibility to make sure that any required privacy policies are guaranteed. # Tests ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py ``` ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/commands/session/save/TestSessionSave.py ``` - Co-authored-by: Roy Shi Co-authored-by: Med Ismail Bennani Added: Modified: lldb/include/lldb/API/SBCommandInterpreter.h lldb/include/lldb/Interpreter/CommandInterpreter.h lldb/source/API/SBCommandInterpreter.cpp lldb/source/Interpreter/CommandInterpreter.cpp lldb/source/Interpreter/InterpreterProperties.td lldb/test/API/commands/session/save/TestSessionSave.py lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py lldb/test/API/python_api/interpreter/main.c Removed: diff --git a/lldb/include/lldb/API/SBCommandInterpreter.h b/lldb/include/lldb/API/SBCommandInterpreter.h index ba2e049204b8e..8ac36344b3a79 100644 --- a/lldb/include/lldb/API/SBCommandInterpreter.h +++ b/lldb/include/lldb/API/SBCommandInterpreter.h @@ -318,6 +318,14 @@ class SBCommandInterpreter { SBStructuredData GetStatistics(); + /// Returns a list of handled commands, output and error. Each element in + /// the list is a dictionary with the following keys/values: + /// - "command" (string): The command that was executed. + /// - "output" (string): The output of the command. Empty ("") if no output. + /// - "error" (string): The error of the command. Empty ("") if no error. + /// - "seconds" (float): The time it took to execute the command. + SBStructuredData GetTranscript(); + protected: friend class lldb_private::CommandPluginInterfaceImplementation; diff --git a/lldb/include/lldb/Interpreter/CommandInterpreter.h b/lldb/include/lldb/Interpreter/CommandInterpreter.h index 70a55a77465bf..ccc30cf4f1a82 100644 --- a/lldb/include/lldb/Interpreter/CommandInterpreter.h +++ b/lldb/include/lldb/Interpreter/CommandInterpreter.h @@ -22,6 +22,7 @@ #include "lldb/Utility/Log.h" #include "lldb/Utility/StreamString.h" #include "lldb/Utility/StringList.h" +#include "lldb/Utility/StructuredData.h" #include "lldb/lldb-forward.h" #include "lldb/lldb-private.h" @@ -560,6 +561,9 @@ clas
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
https://github.com/clayborg closed https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Add new Python API `SBCommandInterpreter::GetTranscript()` (PR #90703)
github-actions[bot] wrote: @royitaqi Congratulations on having your first Pull Request (PR) merged into the LLVM Project! Your changes will be combined with recent changes from other authors, then tested by our [build bots](https://lab.llvm.org/buildbot/). If there is a problem with a build, you may receive a report in an email or a comment on this PR. Please check whether problems have been caused by your change specifically, as the builds can include changes from many authors. It is not uncommon for your change to be included in a build that fails due to someone else's changes, or infrastructure issues. How to do this, and the rest of the post-merge process, is covered in detail [here](https://llvm.org/docs/MyFirstTypoFix.html#myfirsttypofix-issues-after-landing-your-pr). If your change does cause a problem, it may be reverted, or you can revert it yourself. This is a normal part of [LLVM development](https://llvm.org/docs/DeveloperPolicy.html#patch-reversion-policy). You can fix your changes and open a new PR to merge them again. If you don't get any reports, no action is required from you. Your changes are working as expected, well done! https://github.com/llvm/llvm-project/pull/90703 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] 9f62775 - SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (#89868)
Author: royitaqi Date: 2024-05-20T15:51:42-07:00 New Revision: 9f62775038b9135709a2c3c7ea97c944278967a2 URL: https://github.com/llvm/llvm-project/commit/9f62775038b9135709a2c3c7ea97c944278967a2 DIFF: https://github.com/llvm/llvm-project/commit/9f62775038b9135709a2c3c7ea97c944278967a2.diff LOG: SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (#89868) # Motivation Individual callers of `SBDebugger::SetDestroyCallback()` might think that they have registered their callback and expect it to be called when the debugger is destroyed. In reality, only the last caller survives, and all previous callers are forgotten, which might be a surprise to them. Worse, if this is called in a race condition, which callback survives is less predictable, which may case confusing behavior elsewhere. # This PR Allows multiple destroy callbacks to be registered and all called when the debugger is destroyed. **EDIT**: Adds two new APIs: `AddDestroyCallback()` and `ClearDestroyCallback()`. `SetDestroyCallback()` will first clear then add the given callback. Tests are added for the new APIs. ## Tests ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/python_api/debugger/TestDebuggerAPI.py ``` ## (out-dated, see comments below) Semantic change to `SetDestroyCallback()` ~~Currently, the method overwrites the old callback with the new one. With this PR, it will NOT overwrite. Instead, it will hold on to both. Both callbacks get called during destroy.~~ ~~**Risk**: Although the documentation of `SetDestroyCallback()` (see [C++](https://lldb.llvm.org/cpp_reference/classlldb_1_1SBDebugger.html#afa1649d9453a376b5c95888b5a0cb4ec) and [python](https://lldb.llvm.org/python_api/lldb.SBDebugger.html#lldb.SBDebugger.SetDestroyCallback)) doesn't really specify the behavior, there is a risk: if existing call sites rely on the "overwrite" behavior, they will be surprised because now the old callback will get called. But as the above said, the current behavior of "overwrite" itself might be unintended, so I don't anticipate users to rely on this behavior. In short, this risk might be less of a problem if we correct it sooner rather than later (which is what this PR is trying to do).~~ ## (out-dated, see comments below) Implementation ~~The implementation holds a `std::vector>`. When `SetDestroyCallback()` is called, callbacks and batons are appended to the `std::vector`. When destroy event happen, the `(callback, baton)` pairs are invoked FIFO. Finally, the `std::vector` is cleared.~~ # (out-dated, see comments below) Alternatives considered ~~Instead of changing `SetDestroyCallback()`, a new method `AddDestroyCallback()` can be added, which use the same `std::vector>` implementation. Together with `ClearDestroyCallback()` (see below), they will replace and deprecate `SetDestroyCallback()`. Meanwhile, in order to be backward compatible, `SetDestroyCallback()` need to be updated to clear the `std::vector` and then add the new callback. Pros: The end state is semantically more correct. Cons: More steps to take; potentially maintaining an "incorrect" behavior (of "overwrite").~~ ~~A new method `ClearDestroyCallback()` can be added. Might be unnecessary at this point, because workflows which need to set then clear callbacks may exist but shouldn't be too common at least for now. Such method can be added later when needed.~~ ~~The `std::vector` may bring slight performance drawback if its implementation doesn't handle small size efficiently. However, even if that's the case, this path should be very cold (only used during init and destroy). Such performance drawback should be negligible.~~ ~~A different implementation was also considered. Instead of using `std::vector`, the current `m_destroy_callback` field can be kept unchanged. When `SetDestroyCallback()` is called, a lambda function can be stored into `m_destroy_callback`. This lambda function will first call the old callback, then the new one. This way, `std::vector` is avoided. However, this implementation is more complex, thus less readable, with not much perf to gain.~~ - Co-authored-by: Roy Shi Added: Modified: lldb/include/lldb/API/SBDebugger.h lldb/include/lldb/Core/Debugger.h lldb/include/lldb/lldb-types.h lldb/source/API/SBDebugger.cpp lldb/source/Core/Debugger.cpp lldb/test/API/python_api/debugger/TestDebuggerAPI.py Removed: diff --git a/lldb/include/lldb/API/SBDebugger.h b/lldb/include/lldb/API/SBDebugger.h index 7333cd57ad312..af19b1faf3bf5 100644 --- a/lldb/include/lldb/API/SBDebugger.h +++ b/lldb/include/lldb/API/SBDebugger.h @@ -328,9 +328,22 @@ class LLDB_API SBDebugger { void SetLoggingCallback(lldb::LogOutputCallback log_callback, void *baton); + /// Clear all previously added callbacks and only add the given one. + LLDB_DEPRECATED_FIXME("Use AddDestroyCallback and RemoveDestroyCallb
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
https://github.com/clayborg closed https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
github-actions[bot] wrote: @royitaqi Congratulations on having your first Pull Request (PR) merged into the LLVM Project! Your changes will be combined with recent changes from other authors, then tested by our [build bots](https://lab.llvm.org/buildbot/). If there is a problem with a build, you may receive a report in an email or a comment on this PR. Please check whether problems have been caused by your change specifically, as the builds can include changes from many authors. It is not uncommon for your change to be included in a build that fails due to someone else's changes, or infrastructure issues. How to do this, and the rest of the post-merge process, is covered in detail [here](https://llvm.org/docs/MyFirstTypoFix.html#myfirsttypofix-issues-after-landing-your-pr). If your change does cause a problem, it may be reverted, or you can revert it yourself. This is a normal part of [LLVM development](https://llvm.org/docs/DeveloperPolicy.html#patch-reversion-policy). You can fix your changes and open a new PR to merge them again. If you don't get any reports, no action is required from you. Your changes are working as expected, well done! https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -147,96 +148,111 @@ class ProcessInstanceInfo : public ProcessInfo { ProcessInstanceInfo() = default; ProcessInstanceInfo(const char *name, const ArchSpec &arch, lldb::pid_t pid) - : ProcessInfo(name, arch, pid), m_euid(UINT32_MAX), m_egid(UINT32_MAX), -m_parent_pid(LLDB_INVALID_PROCESS_ID) {} + : ProcessInfo(name, arch, pid) {} void Clear() { ProcessInfo::Clear(); -m_euid = UINT32_MAX; -m_egid = UINT32_MAX; -m_parent_pid = LLDB_INVALID_PROCESS_ID; +m_euid = std::nullopt; +m_egid = std::nullopt; +m_parent_pid = std::nullopt; } - uint32_t GetEffectiveUserID() const { return m_euid; } + uint32_t GetEffectiveUserID() const { return m_euid.value(); } clayborg wrote: It is ok to not do all of the ivars at one, but for the `std::optional` stuff that remains, if we just call `.value()` and it hasn't been set we are going to throw an exception right? We either need to make these not optional, or return the optional when accessing and let the callers deal with the values no being available. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
https://github.com/clayborg edited https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -250,10 +268,12 @@ class ProcessInstanceInfo : public ProcessInfo { lldb::pid_t m_parent_pid = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_group_id = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_session_id = LLDB_INVALID_PROCESS_ID; - struct timespec m_user_time {}; - struct timespec m_system_time {}; - struct timespec m_cumulative_user_time {}; - struct timespec m_cumulative_system_time {}; + std::optional m_user_time = std::nullopt; + std::optional m_system_time = std::nullopt; + std::optional m_cumulative_user_time = std::nullopt; + std::optional m_cumulative_system_time = std::nullopt; clayborg wrote: Revert all `struct timespec` optionals because we aren't checking if they have values and we can crash when calling the accessors. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
https://github.com/clayborg requested changes to this pull request. We should either truly use `std::optional` and return `std::optional` for all getters, or just not use them. This patch adds a `bool IsZombieValid()` which the user must know to call prior to calling `bool IsZombie()`, which is just a crash waiting to happen. So lets either use `std::optional` correclty, or remove it and use sane default values. I like the idea of using `std::optional` and suggested ways to provide default values with the `value_or(T)` calls clients can easily use. So might suggest to revert any `struct timespec` optionals since we aren't using them at all, and use `std::optional` and return `std::optional` from the getter functions and have the clients use `value_or(T)` just for these two new functions. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + bool PriorityValueIsValid() const; + + void SetIsZombie(bool is_zombie) { m_zombie = is_zombie; } clayborg wrote: The setter here is fine https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } clayborg wrote: This function should return `std::optional` if we are going to use an optional value for `m_priority_value` as this is just a crash waiting to happen. Callers can provide figure out a good default value to use if this hasn't been set with code like: ``` int8_t priority = proc_info. GetPriorityValue().value_or(0); ``` But as it stands we are going to crash at some point if someone doesn't call `PriorityValueIsValid()` first. So lets either use std::optional and return std::optional, or just default to sane values without optionals. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + bool PriorityValueIsValid() const; + + void SetIsZombie(bool is_zombie) { m_zombie = is_zombie; } + + bool IsZombieValid() const { return m_zombie.has_value(); } + + bool IsZombie() const { return m_zombie.value(); } clayborg wrote: If we are going to use optionals for m_zombie, then we don't need two functions, just return the optional: ``` std::optional GetIsZombie() const { return m_zombie; } ``` And callers will need to check if this has a value and set to a default value like: ``` bool is_zombie = proc_info.GetIsZombie().value_or(false); ``` https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + bool PriorityValueIsValid() const; clayborg wrote: This should be removed as this is the point of using std::optionals. https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -250,10 +268,12 @@ class ProcessInstanceInfo : public ProcessInfo { lldb::pid_t m_parent_pid = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_group_id = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_session_id = LLDB_INVALID_PROCESS_ID; - struct timespec m_user_time {}; - struct timespec m_system_time {}; - struct timespec m_cumulative_user_time {}; - struct timespec m_cumulative_system_time {}; + std::optional m_user_time = std::nullopt; + std::optional m_system_time = std::nullopt; + std::optional m_cumulative_user_time = std::nullopt; + std::optional m_cumulative_system_time = std::nullopt; + std::optional m_priority_value = std::nullopt; + std::optional m_zombie = std::nullopt; clayborg wrote: If we are going to make these optional, then the accessors should return optionals https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [clang] [clang-tools-extra] [compiler-rt] [flang] [libcxx] [libcxxabi] [lld] [lldb] [llvm] [mlir] [BOLT] Ignore special symbols as function aliases in updateELFSymbolTable (PR #92713)
https://github.com/aaupov edited https://github.com/llvm/llvm-project/pull/92713 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [clang] [clang-tools-extra] [compiler-rt] [flang] [libcxx] [libcxxabi] [lld] [lldb] [llvm] [mlir] [BOLT] Ignore special symbols as function aliases in updateELFSymbolTable (PR #92713)
https://github.com/aaupov closed https://github.com/llvm/llvm-project/pull/92713 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Add support for updating string during debug process (PR #67782)
@@ -0,0 +1,171 @@ +#include "LibCxx.h" +#include "LibCxxStringInfoExtractor.h" + +#include "lldb/DataFormatters/FormattersHelpers.h" +#include + +using namespace lldb; +using namespace lldb_private; + +namespace { + +class StringFrontend : public SyntheticChildrenFrontEnd { + +public: + StringFrontend(ValueObject &valobj, const char *prefix = "") + : SyntheticChildrenFrontEnd(valobj), m_prefix(prefix) {} + + llvm::Expected CalculateNumChildren() override { +return m_size + m_special_members_count; + } + + lldb::ValueObjectSP GetChildAtIndex(uint32_t idx) override { + +if (idx < m_special_members_count) { + return m_backend.GetChildMemberWithName(ConstString("__r_"), + /*can_create=*/true); +} + +idx -= m_special_members_count; + +if (!m_str_data_ptr || idx > m_size || !m_element_size) { + return {}; +} + +auto char_it = m_chars.find(idx); +if (char_it != m_chars.end()) { + return char_it->second; +} + +uint64_t offset = idx * m_element_size; +uint64_t address = m_str_data_ptr->GetValueAsUnsigned(0); + +if (!address) { + return {}; +} + +StreamString name; +name.Printf("[%" PRIu64 "]", (uint64_t)idx); + +m_chars[idx] = CreateValueObjectFromAddress( +name.GetString(), address + offset, m_backend.GetExecutionContextRef(), +m_element_type); + +return m_chars[idx]; + } + + size_t GetIndexOfChildWithName(ConstString name) override { +if (name == "__r_") { + return 0; +} +return formatters::ExtractIndexFromString(name.GetCString()) + + m_special_members_count; + } + + ChildCacheState Update() override { + +clear(); + +auto string_info = ExtractLibcxxStringInfo(m_backend); +if (!string_info) + return ChildCacheState::eRefetch; +std::tie(m_size, m_str_data_ptr) = *string_info; + +m_element_type = m_backend.GetCompilerType().GetTypeTemplateArgument(0); +m_element_size = m_element_type.GetByteSize(nullptr).value_or(0); + +if (m_str_data_ptr->IsArrayType()) { + // this means the string is in short-mode and the + // data is stored inline in array, + // so we need address of this array + Status status; + m_str_data_ptr = m_str_data_ptr->AddressOf(status); +} + +return ChildCacheState::eReuse; + } + + bool MightHaveChildren() override { return true; } + + bool SetValueFromCString(const char *value_str, Status &error) override { + +ValueObjectSP expr_value_sp; + +std::unique_lock lock; +ExecutionContext exe_ctx(m_backend.GetExecutionContextRef(), lock); + +Target *target = exe_ctx.GetTargetPtr(); +StackFrame *frame = exe_ctx.GetFramePtr(); + +if (target && frame) { jimingham wrote: I don't think this is the right way to implement this. By relying on the base name of the backend and using that directly you will only be able to handle cases where the std::string is a local variable or function argument. It won't work on std::strings inside other objects - you would need the full path. It also won't work for globals, which don't have frames, even though there's no reason it shouldn't. A better approach would be to get the address of the object you are trying to change, and using that address properly cast to do the assignment. That way you wouldn't have to care how that value got referred to. For the most part we try not to run expressions in the ValueObject code, but setting values is less likely to happen for large objects, or to lots of variables at once the way rendering their values/Summaries, etc does. But you certainly shouldn't run expressions on a ValueObject's behalf that allow more than one thread to run. Otherwise you get into the state where I stop in thread A, see something interesting, go to thread B and change a value and switch back to thread A and it's not where I left it! https://github.com/llvm/llvm-project/pull/67782 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Add support for updating string during debug process (PR #67782)
https://github.com/jimingham edited https://github.com/llvm/llvm-project/pull/67782 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Add support for updating string during debug process (PR #67782)
jimingham wrote: > Hello, @jimingham , first of all - sorry for the long delay in reply. > > I carefully read through all your messages once again and found, that I > totally misunderstood some places, i.e. "Why isn't it enough to have the > ValueObjectSynthetic's SetValueFromCString do this" - I think it should be > enough, I'll fix it. > > > Secondly, lldb only supports changing scalars because it's hard to give > > meaning to "changing an aggregate object". You have to change it in situ - > > which really means changing the values of its contents, i.e. its children - > > or you will end up invalidating code that relies on the location of the > > aggregate > > I agree with this, but I think there is not so much aggregates for which it > makes sense to change their length as for strings (at least in libcxx) - I > mean it is natural to update whole string to completely different value, but > it is not natural to do so for e.g. vector. In case of strings, one might > want to set string longer, than the one he has now for the debug purposes, so > this will indeed invalidate code, that relies on the pointers that was > obtained through `.data` or `.c_str` methods, but it is the programmer > responsibility to care about this. This it the same behaviour as if you > change your string in the program - you should update your pointers. It's not just pointers, of course. If you've done: size_t string_len = my_string.size(); then string_len will be wrong. But I agree, that's more the lookout of whoever is messing with their strings while running. > > > However, I think it's confusing here to start with the model that > > ValueObjects with SCPs have "underlying strings". > > Sorry, I think that I didn't express my thoughts carefully, by the underlying > string I didn't mean, that we have some string in the SCP or ValueObjects, I > meant the strings in the code that is under debug. > > > By the way, as a side note, watching the part of your example where you > > change the raw string guts, it looks like we don't update summaries of a > > ValueObject if one of its children gets changed. Be good to file bug on > > that one so we don't forget. > > I'm not sure that this bug might be reproduced without the string example, I > don't know which type have the summary which represent all its children. Is > it ok, to file a bug with current strings example or how to do it better? > > > In the case of std::strings, which seems to be your primary motivator here, > > I think considering the string value to be the summary makes the most sense > > And in the end, may I kindly ask you to clarify your position about these > changes please? Do you suggest to return to the `SetSummaryFromCString` API? The more I think about it, the more it seems that SetSummaryFromCString is just the wrong API to use to change the value of something. After all, Summaries don't actually represent the "value" of the ValueObject, they are just whatever bits of that value the Summary Provider decided to extract, plus whatever additional text they wanted to provide. Summaries may not even be about the value at all, for instance for checked pointers they might just say the checked state. It's clear that's not the entity you would ask to change that object's value. `std::string` and `char *` seem different because we show the string contents in the summary, and people like to pretend that the "value" of a std::string or char * is the extracted string contents, though that's not really true. So I don't think trying to change underlying values makes sense as part of the Summary feature. Changing values of a ValueObject with a Synthetic Child Provider definitely makes sense if directed to the children the synthetic child provider shows. If the SCP for some value produces an `int` child named `my_made_up_child`, then it would make sense to ask it if it can change the value of whatever underlies `my_made_up_child`. That also has a straight-forward interface, you get a SCP's child, and set its value, which the SCP Frontend intercepts, and does what is needed to change the value if it can. If we were presenting the std::string contents as an array of char's then changing the individual characters by addressing the members of the array would make sense. Note, that's also the only interface that will work for std::string's in full generality because std::strings aren't required to hold null-terminated C-strings. I'm a little bothered by the notion of changing the whole of a SyntheticValue by providing some C-string. That makes sense for a restricted representation of the new values of something that stores string-y objects, but doesn't make sense without further syntax for anything else. It's also not the right implementation internally for changing the child provided by an SCP, since it that case you'd call SetValueFromCString on the child, and route that to the parent. But havi
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
https://github.com/jasonmolenda commented: I read this patch while trying to keep the RVC instruction set in mind because it's an interesting case to consider. Maybe the test file could have a compressed instruction? The one instruction there now ends in 0b11 so I don't think it will decode that way. https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
@@ -99,6 +100,8 @@ class EmulateInstructionRISCV : public EmulateInstruction { private: /// Last decoded instruction from m_opcode DecodeResult m_decoded; + /// Last tried to be decoded instruction expected size. jasonmolenda wrote: I might call this `Last decoded instruction size`. https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
@@ -115,8 +148,23 @@ Status NativeProcessSoftwareSingleStep::SetupSoftwareSingleStepping( emulator_up->SetWriteMemCallback(&WriteMemoryCallback); emulator_up->SetWriteRegCallback(&WriteRegisterCallback); - if (!emulator_up->ReadInstruction()) -return Status("Read instruction failed!"); + if (!emulator_up->ReadInstruction()) { +// try to get at least the size of next instruction to set breakpoint. +auto instrSizeOpt = emulator_up->GetLastInstrSize(); +if (!instrSizeOpt) + return Status("Read instruction failed!"); jasonmolenda wrote: We've defined the new GetLastInstrSize() method for the RISCV EmulateInstruction plugin, but others like AArch64 won't have that, so this will error out on them, won't it? What we really want to express is "if `arch.GetTriple().isRISCV()` and we couldn't decode the length of the last instruction, then error out" isn't it? https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
@@ -115,8 +148,23 @@ Status NativeProcessSoftwareSingleStep::SetupSoftwareSingleStepping( emulator_up->SetWriteMemCallback(&WriteMemoryCallback); emulator_up->SetWriteRegCallback(&WriteRegisterCallback); - if (!emulator_up->ReadInstruction()) -return Status("Read instruction failed!"); + if (!emulator_up->ReadInstruction()) { jasonmolenda wrote: Shouldn't this block now be `if (emulator_up->ReadInstruction())` now? We're going to get the size of the last decoded instruction here. https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
@@ -115,8 +148,23 @@ Status NativeProcessSoftwareSingleStep::SetupSoftwareSingleStepping( emulator_up->SetWriteMemCallback(&WriteMemoryCallback); emulator_up->SetWriteRegCallback(&WriteRegisterCallback); - if (!emulator_up->ReadInstruction()) -return Status("Read instruction failed!"); + if (!emulator_up->ReadInstruction()) { +// try to get at least the size of next instruction to set breakpoint. +auto instrSizeOpt = emulator_up->GetLastInstrSize(); +if (!instrSizeOpt) + return Status("Read instruction failed!"); +bool success = false; +auto pc = emulator_up->ReadRegisterUnsigned(eRegisterKindGeneric, +LLDB_REGNUM_GENERIC_PC, +LLDB_INVALID_ADDRESS, &success); +if (!success) + return Status("Reading pc failed!"); +lldb::addr_t next_pc = pc + *instrSizeOpt; +auto Result = +SetSoftwareBreakPointOnPC(arch, next_pc, /* next_flags */ 0x0, process); jasonmolenda wrote: We've decoded the length of the instruction at `pc` at this point, and them to get `next_pc`. Then we pass `next_pc` to this method which has a hardcoded size of 4 for RISCV. It's only a hint that is sent to lldb-server as it tries to step over the instruction. With armv7/aarch32 we had to get arm/thumb breakpoint instructions correct because an arm breakpoint wasn't valid when the processor was in thumb mode (iirc) but RISC-V doesn't have a processor mode like that iiuc. So maybe it's fine to have `SetSoftwareBreakPointOnPC` hardcoding 4 for the next RISCV breakpoint. https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
https://github.com/jasonmolenda edited https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Reapply "[lldb/aarch64] Fix unwinding when signal interrupts a leaf f… (PR #92503)
jasonmolenda wrote: Yes, originally lldb's unwinder was recursive for any register propagation and it was easy to hit the problem of lldb blowing out its own stack on a recursive inferior that had crashed. I changed most of the propagation to a loop to solve this (years and years ago) but it looks like we still have a case where it is recursing. We still need to skip the test case on macOS until I can come up with some idea to get proper unwind instruction for sigtramp on arm64. Most of the CI bots are x86_64 so it may pass on them, but that's The Past and I would prefer to skip this on Darwin until I can figure something out, I wrote a little TODO on myself in rdar://128031075 This looks good to me. https://github.com/llvm/llvm-project/pull/92503 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Reapply "[lldb/aarch64] Fix unwinding when signal interrupts a leaf f… (PR #92503)
https://github.com/jasonmolenda approved this pull request. LGTM https://github.com/llvm/llvm-project/pull/92503 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Add the word "backtrace" to bt help string (PR #92618)
https://github.com/jasonmolenda approved this pull request. looks good, thanks. https://github.com/llvm/llvm-project/pull/92618 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
@@ -115,8 +148,23 @@ Status NativeProcessSoftwareSingleStep::SetupSoftwareSingleStepping( emulator_up->SetWriteMemCallback(&WriteMemoryCallback); emulator_up->SetWriteRegCallback(&WriteRegisterCallback); - if (!emulator_up->ReadInstruction()) -return Status("Read instruction failed!"); + if (!emulator_up->ReadInstruction()) { jasonmolenda wrote: Ah wait, I see. This method is trying to decode where the next instruction will go, with branches and jumps decoded, so we can put a breakpoint there. And you're handling the case where we can't decode the current instruction (I now understand why you used that in your test case). It seems harmless to call GetLastInstrSize() if the instruction that couldn't be decoded, and add the length of the instruction to pc. We can assume the emulation engine will emulate all branching instructions. I could imagine the RISCV emulation plugin didn't have decoding for an instruction that doesn't branch, it could fail, but we can still decode the size of that unknown instruction successfully, and assume that it does not branch. https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
https://github.com/feg208 updated https://github.com/llvm/llvm-project/pull/91544 >From 8f694b7ab4436c0540284cbbf280ad557a750920 Mon Sep 17 00:00:00 2001 From: Fred Grim Date: Wed, 8 May 2024 15:36:16 -0700 Subject: [PATCH] [lldb] Adds additional fields to ProcessInfo To implement SaveCore for elf binaries we need to populate some additional fields in the prpsinfo struct. Those fields are the nice value of the process whose core is to be taken as well as a boolean flag indicating whether or not that process is a zombie. This commit adds those as well as tests to ensure that the values are consistent with expectations --- lldb/include/lldb/Utility/ProcessInfo.h | 24 ++- lldb/source/Host/linux/Host.cpp | 32 ++--- lldb/source/Utility/ProcessInfo.cpp | 7 +++--- lldb/unittests/Host/linux/HostTest.cpp | 21 4 files changed, 67 insertions(+), 17 deletions(-) diff --git a/lldb/include/lldb/Utility/ProcessInfo.h b/lldb/include/lldb/Utility/ProcessInfo.h index 54ac000dc7fc2..78ade4bbb1ee6 100644 --- a/lldb/include/lldb/Utility/ProcessInfo.h +++ b/lldb/include/lldb/Utility/ProcessInfo.h @@ -15,6 +15,7 @@ #include "lldb/Utility/FileSpec.h" #include "lldb/Utility/NameMatches.h" #include "lldb/Utility/StructuredData.h" +#include #include namespace lldb_private { @@ -147,8 +148,7 @@ class ProcessInstanceInfo : public ProcessInfo { ProcessInstanceInfo() = default; ProcessInstanceInfo(const char *name, const ArchSpec &arch, lldb::pid_t pid) - : ProcessInfo(name, arch, pid), m_euid(UINT32_MAX), m_egid(UINT32_MAX), -m_parent_pid(LLDB_INVALID_PROCESS_ID) {} + : ProcessInfo(name, arch, pid) {} void Clear() { ProcessInfo::Clear(); @@ -237,6 +237,16 @@ class ProcessInstanceInfo : public ProcessInfo { m_cumulative_system_time.tv_usec > 0; } + std::optional GetPriorityValue() const { return m_priority_value; } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + void SetIsZombie(bool is_zombie) { m_zombie = is_zombie; } + + std::optional IsZombie() const { return m_zombie; } + void Dump(Stream &s, UserIDResolver &resolver) const; static void DumpTableHeader(Stream &s, bool show_args, bool verbose); @@ -250,10 +260,12 @@ class ProcessInstanceInfo : public ProcessInfo { lldb::pid_t m_parent_pid = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_group_id = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_session_id = LLDB_INVALID_PROCESS_ID; - struct timespec m_user_time {}; - struct timespec m_system_time {}; - struct timespec m_cumulative_user_time {}; - struct timespec m_cumulative_system_time {}; + struct timespec m_user_time; + struct timespec m_system_time; + struct timespec m_cumulative_user_time; + struct timespec m_cumulative_system_time; + std::optional m_priority_value = std::nullopt; + std::optional m_zombie = std::nullopt; }; typedef std::vector ProcessInstanceInfoList; diff --git a/lldb/source/Host/linux/Host.cpp b/lldb/source/Host/linux/Host.cpp index c6490f2fc9e2f..5545f9ef4d70e 100644 --- a/lldb/source/Host/linux/Host.cpp +++ b/lldb/source/Host/linux/Host.cpp @@ -37,6 +37,7 @@ using namespace lldb; using namespace lldb_private; namespace { + enum class ProcessState { Unknown, Dead, @@ -70,6 +71,12 @@ struct StatFields { long unsigned stime; long cutime; long cstime; + // In proc_pid_stat(5) this field is specified as priority + // but documented as realtime priority. To keep with the adopted + // nomenclature in ProcessInstanceInfo, we adopt the documented + // naming here. + long realtime_priority; + long priority; // other things. We don't need them below }; } @@ -91,14 +98,16 @@ static bool GetStatusInfo(::pid_t Pid, ProcessInstanceInfo &ProcessInfo, if (Rest.empty()) return false; StatFields stat_fields; - if (sscanf(Rest.data(), - "%d %s %c %d %d %d %d %d %u %lu %lu %lu %lu %lu %lu %ld %ld", - &stat_fields.pid, stat_fields.comm, &stat_fields.state, - &stat_fields.ppid, &stat_fields.pgrp, &stat_fields.session, - &stat_fields.tty_nr, &stat_fields.tpgid, &stat_fields.flags, - &stat_fields.minflt, &stat_fields.cminflt, &stat_fields.majflt, - &stat_fields.cmajflt, &stat_fields.utime, &stat_fields.stime, - &stat_fields.cutime, &stat_fields.cstime) < 0) { + if (sscanf( + Rest.data(), + "%d %s %c %d %d %d %d %d %u %lu %lu %lu %lu %lu %lu %ld %ld %ld %ld", + &stat_fields.pid, stat_fields.comm, &stat_fields.state, + &stat_fields.ppid, &stat_fields.pgrp, &stat_fields.session, + &stat_fields.tty_nr, &stat_fields.tpgid, &stat_fields.flags, + &stat_fields.minflt, &stat_fields.cminflt, &stat_fields.majflt, + &stat_fields.cmajflt, &stat_fields.utime, &stat_fields.stime, + &stat_fields.cutime, &stat_fields.cstime
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -147,96 +148,111 @@ class ProcessInstanceInfo : public ProcessInfo { ProcessInstanceInfo() = default; ProcessInstanceInfo(const char *name, const ArchSpec &arch, lldb::pid_t pid) - : ProcessInfo(name, arch, pid), m_euid(UINT32_MAX), m_egid(UINT32_MAX), -m_parent_pid(LLDB_INVALID_PROCESS_ID) {} + : ProcessInfo(name, arch, pid) {} void Clear() { ProcessInfo::Clear(); -m_euid = UINT32_MAX; -m_egid = UINT32_MAX; -m_parent_pid = LLDB_INVALID_PROCESS_ID; +m_euid = std::nullopt; +m_egid = std::nullopt; +m_parent_pid = std::nullopt; } - uint32_t GetEffectiveUserID() const { return m_euid; } + uint32_t GetEffectiveUserID() const { return m_euid.value(); } feg208 wrote: yeah. I of the same view https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
https://github.com/feg208 edited https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -250,10 +268,12 @@ class ProcessInstanceInfo : public ProcessInfo { lldb::pid_t m_parent_pid = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_group_id = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_session_id = LLDB_INVALID_PROCESS_ID; - struct timespec m_user_time {}; - struct timespec m_system_time {}; - struct timespec m_cumulative_user_time {}; - struct timespec m_cumulative_system_time {}; + std::optional m_user_time = std::nullopt; + std::optional m_system_time = std::nullopt; + std::optional m_cumulative_user_time = std::nullopt; + std::optional m_cumulative_system_time = std::nullopt; feg208 wrote: done https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -250,10 +268,12 @@ class ProcessInstanceInfo : public ProcessInfo { lldb::pid_t m_parent_pid = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_group_id = LLDB_INVALID_PROCESS_ID; lldb::pid_t m_process_session_id = LLDB_INVALID_PROCESS_ID; - struct timespec m_user_time {}; - struct timespec m_system_time {}; - struct timespec m_cumulative_user_time {}; - struct timespec m_cumulative_system_time {}; + std::optional m_user_time = std::nullopt; + std::optional m_system_time = std::nullopt; + std::optional m_cumulative_user_time = std::nullopt; + std::optional m_cumulative_system_time = std::nullopt; + std::optional m_priority_value = std::nullopt; + std::optional m_zombie = std::nullopt; feg208 wrote: done https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + bool PriorityValueIsValid() const; + + void SetIsZombie(bool is_zombie) { m_zombie = is_zombie; } + + bool IsZombieValid() const { return m_zombie.has_value(); } + + bool IsZombie() const { return m_zombie.value(); } feg208 wrote: done https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } feg208 wrote: done https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
@@ -195,48 +195,66 @@ class ProcessInstanceInfo : public ProcessInfo { return m_process_session_id != LLDB_INVALID_PROCESS_ID; } - struct timespec GetUserTime() const { return m_user_time; } + struct timespec GetUserTime() const { return m_user_time.value(); } void SetUserTime(struct timespec utime) { m_user_time = utime; } bool UserTimeIsValid() const { -return m_user_time.tv_sec > 0 || m_user_time.tv_usec > 0; +return m_user_time.has_value() && + (m_user_time->tv_sec > 0 || m_user_time->tv_usec > 0); } - struct timespec GetSystemTime() const { return m_system_time; } + struct timespec GetSystemTime() const { return m_system_time.value(); } void SetSystemTime(struct timespec stime) { m_system_time = stime; } bool SystemTimeIsValid() const { -return m_system_time.tv_sec > 0 || m_system_time.tv_usec > 0; +return m_system_time.has_value() && + (m_system_time->tv_sec > 0 || m_system_time->tv_usec > 0); } struct timespec GetCumulativeUserTime() const { -return m_cumulative_user_time; +return m_cumulative_user_time.value(); } void SetCumulativeUserTime(struct timespec cutime) { m_cumulative_user_time = cutime; } bool CumulativeUserTimeIsValid() const { -return m_cumulative_user_time.tv_sec > 0 || - m_cumulative_user_time.tv_usec > 0; +return m_cumulative_user_time.has_value() && + (m_cumulative_user_time->tv_sec > 0 || +m_cumulative_user_time->tv_usec > 0); } struct timespec GetCumulativeSystemTime() const { -return m_cumulative_system_time; +return m_cumulative_system_time.value(); } void SetCumulativeSystemTime(struct timespec cstime) { m_cumulative_system_time = cstime; } bool CumulativeSystemTimeIsValid() const { -return m_cumulative_system_time.tv_sec > 0 || - m_cumulative_system_time.tv_usec > 0; +return m_cumulative_system_time.has_value() && + (m_cumulative_system_time->tv_sec > 0 || +m_cumulative_system_time->tv_usec > 0); } + int8_t GetPriorityValue() const { return m_priority_value.value(); } + + void SetPriorityValue(int8_t priority_value) { +m_priority_value = priority_value; + } + + bool PriorityValueIsValid() const; feg208 wrote: done https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Adds additional fields to ProcessInfo (PR #91544)
feg208 wrote: @clayborg I rolled up those requested changes. That'll make a nicer interface https://github.com/llvm/llvm-project/pull/91544 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][riscv] Fix setting breakpoint for undecoded instruction (PR #90075)
https://github.com/jasonmolenda edited https://github.com/llvm/llvm-project/pull/90075 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] A few updates around "transcript" (PR #92843)
https://github.com/royitaqi created https://github.com/llvm/llvm-project/pull/92843 # Changes 1. Add `resolvedCommand` as a new field to (structured) transcript. This field will hold the expanded/executed command (e.g. "breakpoint set ..."). This is not to be confused with the "command" field, which holds the user input (e.g. "br s ..."). 2. When transcript is available, add it to the output of `statistics dump`. 3. A few minor comment and test name changes. # Test ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/commands/statistics/basic/TestStats.py ``` ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py ``` >From 8499f16ad46b3268f35da2bfcbfa02a10aab935a Mon Sep 17 00:00:00 2001 From: Roy Shi Date: Mon, 20 May 2024 22:30:40 -0400 Subject: [PATCH 1/3] Add resolvedCommand to transcript, add transcript to statistics dump --- lldb/include/lldb/API/SBCommandInterpreter.h | 3 +- .../lldb/Interpreter/CommandInterpreter.h | 5 +-- .../source/Interpreter/CommandInterpreter.cpp | 6 lldb/source/Target/Statistics.cpp | 31 +++ .../commands/statistics/basic/TestStats.py| 30 ++ .../interpreter/TestCommandInterpreterAPI.py | 20 6 files changed, 86 insertions(+), 9 deletions(-) diff --git a/lldb/include/lldb/API/SBCommandInterpreter.h b/lldb/include/lldb/API/SBCommandInterpreter.h index 8ac36344b3a79..8eb4a71cb7f88 100644 --- a/lldb/include/lldb/API/SBCommandInterpreter.h +++ b/lldb/include/lldb/API/SBCommandInterpreter.h @@ -320,7 +320,8 @@ class SBCommandInterpreter { /// Returns a list of handled commands, output and error. Each element in /// the list is a dictionary with the following keys/values: - /// - "command" (string): The command that was executed. + /// - "command" (string): The command that was given by the user. + /// - "resolvedCommand" (string): The expanded command that was executed. /// - "output" (string): The output of the command. Empty ("") if no output. /// - "error" (string): The error of the command. Empty ("") if no error. /// - "seconds" (float): The time it took to execute the command. diff --git a/lldb/include/lldb/Interpreter/CommandInterpreter.h b/lldb/include/lldb/Interpreter/CommandInterpreter.h index ccc30cf4f1a82..7f420daca450a 100644 --- a/lldb/include/lldb/Interpreter/CommandInterpreter.h +++ b/lldb/include/lldb/Interpreter/CommandInterpreter.h @@ -580,7 +580,7 @@ class CommandInterpreter : public Broadcaster, void SetEchoCommentCommands(bool enable); bool GetRepeatPreviousCommand() const; - + bool GetRequireCommandOverwrite() const; const CommandObject::CommandMap &GetUserCommands() const { @@ -776,7 +776,8 @@ class CommandInterpreter : public Broadcaster, /// Contains a list of handled commands and their details. Each element in /// the list is a dictionary with the following keys/values: - /// - "command" (string): The command that was executed. + /// - "command" (string): The command that was given by the user. + /// - "resolvedCommand" (string): The expanded command that was executed. /// - "output" (string): The output of the command. Empty ("") if no output. /// - "error" (string): The error of the command. Empty ("") if no error. /// - "seconds" (float): The time it took to execute the command. diff --git a/lldb/source/Interpreter/CommandInterpreter.cpp b/lldb/source/Interpreter/CommandInterpreter.cpp index 811726e30af4d..04820bd7d39f6 100644 --- a/lldb/source/Interpreter/CommandInterpreter.cpp +++ b/lldb/source/Interpreter/CommandInterpreter.cpp @@ -2011,6 +2011,12 @@ bool CommandInterpreter::HandleCommand(const char *command_line, wants_raw_input ? "True" : "False"); } + // To test whether or not transcript should be saved, `transcript_item` is + // used instead of `GetSaveTrasncript()`. This is because the latter will + // fail when the command is "settings set interpreter.save-transcript true". + if (transcript_item) +transcript_item->AddStringItem("resolvedCommand", command_string); + // Phase 2. // Take care of things like setting up the history command & calling the // appropriate Execute method on the CommandObject, with the appropriate diff --git a/lldb/source/Target/Statistics.cpp b/lldb/source/Target/Statistics.cpp index 7f866ae0ef324..fd31377abd06b 100644 --- a/lldb/source/Target/Statistics.cpp +++ b/lldb/source/Target/Statistics.cpp @@ -16,6 +16,7 @@ #include "lldb/Target/Process.h" #include "lldb/Target/Target.h" #include "lldb/Target/UnixSignals.h" +#include "lldb/Utility/StructuredData.h" using namespace lldb; using namespace lldb_private; @@ -362,6 +363,36 @@ llvm::json::Value DebuggerStats::ReportStatistics( global_stats.try_emplace("modules", std::move(json_modules)); global_stats.try_emplace("memory", std::move(json_memory)); global_stats.try_emplace("commands", std::m
[Lldb-commits] [lldb] A few updates around "transcript" (PR #92843)
llvmbot wrote: @llvm/pr-subscribers-lldb Author: None (royitaqi) Changes # Changes 1. Add `resolvedCommand` as a new field to (structured) transcript. This field will hold the expanded/executed command (e.g. "breakpoint set ..."). This is not to be confused with the "command" field, which holds the user input (e.g. "br s ..."). 2. When transcript is available, add it to the output of `statistics dump`. 3. A few minor comment and test name changes. # Test ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/commands/statistics/basic/TestStats.py ``` ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py ``` --- Full diff: https://github.com/llvm/llvm-project/pull/92843.diff 6 Files Affected: - (modified) lldb/include/lldb/API/SBCommandInterpreter.h (+2-1) - (modified) lldb/include/lldb/Interpreter/CommandInterpreter.h (+2-1) - (modified) lldb/source/Interpreter/CommandInterpreter.cpp (+6) - (modified) lldb/source/Target/Statistics.cpp (+31) - (modified) lldb/test/API/commands/statistics/basic/TestStats.py (+30) - (modified) lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py (+14-6) ``diff diff --git a/lldb/include/lldb/API/SBCommandInterpreter.h b/lldb/include/lldb/API/SBCommandInterpreter.h index 8ac36344b3a79..8eb4a71cb7f88 100644 --- a/lldb/include/lldb/API/SBCommandInterpreter.h +++ b/lldb/include/lldb/API/SBCommandInterpreter.h @@ -320,7 +320,8 @@ class SBCommandInterpreter { /// Returns a list of handled commands, output and error. Each element in /// the list is a dictionary with the following keys/values: - /// - "command" (string): The command that was executed. + /// - "command" (string): The command that was given by the user. + /// - "resolvedCommand" (string): The expanded command that was executed. /// - "output" (string): The output of the command. Empty ("") if no output. /// - "error" (string): The error of the command. Empty ("") if no error. /// - "seconds" (float): The time it took to execute the command. diff --git a/lldb/include/lldb/Interpreter/CommandInterpreter.h b/lldb/include/lldb/Interpreter/CommandInterpreter.h index ccc30cf4f1a82..6e21af7180f79 100644 --- a/lldb/include/lldb/Interpreter/CommandInterpreter.h +++ b/lldb/include/lldb/Interpreter/CommandInterpreter.h @@ -776,7 +776,8 @@ class CommandInterpreter : public Broadcaster, /// Contains a list of handled commands and their details. Each element in /// the list is a dictionary with the following keys/values: - /// - "command" (string): The command that was executed. + /// - "command" (string): The command that was given by the user. + /// - "resolvedCommand" (string): The expanded command that was executed. /// - "output" (string): The output of the command. Empty ("") if no output. /// - "error" (string): The error of the command. Empty ("") if no error. /// - "seconds" (float): The time it took to execute the command. diff --git a/lldb/source/Interpreter/CommandInterpreter.cpp b/lldb/source/Interpreter/CommandInterpreter.cpp index 811726e30af4d..04820bd7d39f6 100644 --- a/lldb/source/Interpreter/CommandInterpreter.cpp +++ b/lldb/source/Interpreter/CommandInterpreter.cpp @@ -2011,6 +2011,12 @@ bool CommandInterpreter::HandleCommand(const char *command_line, wants_raw_input ? "True" : "False"); } + // To test whether or not transcript should be saved, `transcript_item` is + // used instead of `GetSaveTrasncript()`. This is because the latter will + // fail when the command is "settings set interpreter.save-transcript true". + if (transcript_item) +transcript_item->AddStringItem("resolvedCommand", command_string); + // Phase 2. // Take care of things like setting up the history command & calling the // appropriate Execute method on the CommandObject, with the appropriate diff --git a/lldb/source/Target/Statistics.cpp b/lldb/source/Target/Statistics.cpp index 7f866ae0ef324..fd31377abd06b 100644 --- a/lldb/source/Target/Statistics.cpp +++ b/lldb/source/Target/Statistics.cpp @@ -16,6 +16,7 @@ #include "lldb/Target/Process.h" #include "lldb/Target/Target.h" #include "lldb/Target/UnixSignals.h" +#include "lldb/Utility/StructuredData.h" using namespace lldb; using namespace lldb_private; @@ -362,6 +363,36 @@ llvm::json::Value DebuggerStats::ReportStatistics( global_stats.try_emplace("modules", std::move(json_modules)); global_stats.try_emplace("memory", std::move(json_memory)); global_stats.try_emplace("commands", std::move(cmd_stats)); + +// When transcript is available, add it to the to-be-returned statistics. +// +// NOTE: +// When the statistics is polled by an LLDB command: +// - The transcript in the returned statistics *will NOT* contain the +// returned statistics itself. +// - The returned statistics *will* be written to the internal transcript +// buffer as the outp
[Lldb-commits] [lldb] A few updates around "transcript" (PR #92843)
github-actions[bot] wrote: :warning: Python code formatter, darker found issues in your code. :warning: You can test this locally with the following command: ``bash darker --check --diff -r 85e1124049cd8aa1e58c101e082100ba74df7e42...67a1197a15682731f37890734a5c8674896e0428 lldb/test/API/commands/statistics/basic/TestStats.py lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py `` View the diff from darker here. ``diff --- commands/statistics/basic/TestStats.py 2024-05-21 02:30:40.00 + +++ commands/statistics/basic/TestStats.py 2024-05-21 02:48:21.570474 + @@ -622,34 +622,35 @@ # Verify that the top level statistic that aggregates the number of # modules with debugInfoHadVariableErrors is greater than zero self.assertGreater(stats["totalModuleCountWithVariableErrors"], 0) + def test_transcript(self): -""" -Test "statistics dump" and the transcript information. -""" -self.build() -exe = self.getBuildArtifact("a.out") -target = self.createTestTarget(file_path=exe) -self.runCmd("settings set target.save-transcript true") -self.runCmd("version") - -# Verify the output of a first "statistics dump" -debug_stats = self.get_stats() -self.assertIn("transcript", debug_stats) -transcript = debug_stats["transcript"] -self.assertEqual(len(transcript), 2) -self.assertEqual(transcript[0]["command"], "version") -self.assertEqual(transcript[1]["command"], "statistics dump") -self.assertEqual(transcript[1]["output"], "") - -# Verify the output of a second "statistics dump" -debug_stats = self.get_stats() -self.assertIn("transcript", debug_stats) -transcript = debug_stats["transcript"] -self.assertEqual(len(transcript), 3) -self.assertEqual(transcript[0]["command"], "version") -self.assertEqual(transcript[1]["command"], "statistics dump") -self.assertNotEqual(transcript[1]["output"], "") -self.assertEqual(transcript[2]["command"], "statistics dump") -self.assertEqual(transcript[2]["output"], "") +""" +Test "statistics dump" and the transcript information. +""" +self.build() +exe = self.getBuildArtifact("a.out") +target = self.createTestTarget(file_path=exe) +self.runCmd("settings set target.save-transcript true") +self.runCmd("version") + +# Verify the output of a first "statistics dump" +debug_stats = self.get_stats() +self.assertIn("transcript", debug_stats) +transcript = debug_stats["transcript"] +self.assertEqual(len(transcript), 2) +self.assertEqual(transcript[0]["command"], "version") +self.assertEqual(transcript[1]["command"], "statistics dump") +self.assertEqual(transcript[1]["output"], "") + +# Verify the output of a second "statistics dump" +debug_stats = self.get_stats() +self.assertIn("transcript", debug_stats) +transcript = debug_stats["transcript"] +self.assertEqual(len(transcript), 3) +self.assertEqual(transcript[0]["command"], "version") +self.assertEqual(transcript[1]["command"], "statistics dump") +self.assertNotEqual(transcript[1]["output"], "") +self.assertEqual(transcript[2]["command"], "statistics dump") +self.assertEqual(transcript[2]["output"], "") --- python_api/interpreter/TestCommandInterpreterAPI.py 2024-05-21 02:42:42.00 + +++ python_api/interpreter/TestCommandInterpreterAPI.py 2024-05-21 02:48:21.667109 + @@ -160,11 +160,14 @@ "error": "error: 'an-unknown-command' is not a valid command.\n", }) # (lldb) br s -f main.c -l self.assertEqual(transcript[2]["command"], "br s -f main.c -l %d" % self.line) -self.assertEqual(transcript[2]["resolvedCommand"], "breakpoint set -f main.c -l %d" % self.line) +self.assertEqual( +transcript[2]["resolvedCommand"], +"breakpoint set -f main.c -l %d" % self.line, +) # Breakpoint 1: where = a.out`main + 29 at main.c:5:3, address = 0x00010f7d self.assertIn("Breakpoint 1: where = a.out`main ", transcript[2]["output"]) self.assertEqual(transcript[2]["error"], "") # (lldb) r `` https://github.com/llvm/llvm-project/pull/92843 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [clang] [compiler-rt] [lldb] [llvm] [Support] Remove terminfo dependency (PR #92865)
https://github.com/aaronmondal created https://github.com/llvm/llvm-project/pull/92865 The terminfo dependency introduces a significant nonhermeticity into the build. It doesn't respect `--no-undefined-version` meaning that it's not a dependency that can be built with Clang 17+. This forces maintainers of source-based distributions to implement patches or ignore linker errors. Remove it to reduce the closure size and improve portability of LLVM-based tools. Users can still use command line arguments to toggle color support expliticly. Fixes #75490 Closes #53294 #23355 >From 404dcfceb9c073c3a055a7242ddf05c1f36111a2 Mon Sep 17 00:00:00 2001 From: Aaron Siddhartha Mondal Date: Tue, 21 May 2024 06:37:49 +0200 Subject: [PATCH] [Support] Remove terminfo dependency The terminfo dependency introduces a significant nonhermeticity into the build. It doesn't respect `--no-undefined-version` meaning that it's not a dependency that can be built with Clang 17+. This forces maintainers of source-based distributions to implement patches or ignore linker errors. Remove it to reduce the closure size and improve portability of LLVM-based tools. Users can still use command line arguments to toggle color support expliticly. Fixes #75490 Closes #53294 #23355 --- clang/cmake/caches/Fuchsia-stage2.cmake | 1 - clang/cmake/caches/Fuchsia.cmake | 7 --- clang/cmake/caches/VectorEngine.cmake | 4 +- clang/utils/analyzer/entrypoint.py| 2 +- compiler-rt/cmake/config-ix.cmake | 15 - .../symbolizer/scripts/build_symbolizer.sh| 1 - compiler-rt/lib/xray/tests/CMakeLists.txt | 5 -- lldb/docs/resources/build.rst | 1 - lldb/source/Core/CMakeLists.txt | 3 - llvm/CMakeLists.txt | 2 - llvm/cmake/config-ix.cmake| 10 llvm/cmake/modules/FindTerminfo.cmake | 55 - llvm/cmake/modules/LLVMConfig.cmake.in| 5 -- llvm/docs/ReleaseNotes.rst| 4 ++ llvm/include/llvm/Config/config.h.cmake | 3 - llvm/lib/Support/CMakeLists.txt | 11 llvm/lib/Support/Unix/Process.inc | 60 ++- llvm/utils/gn/README.rst | 2 +- llvm/utils/gn/build/libs/terminfo/BUILD.gn| 12 llvm/utils/gn/build/libs/terminfo/enable.gni | 4 -- .../llvm/include/llvm/Config/BUILD.gn | 7 --- .../gn/secondary/llvm/lib/Support/BUILD.gn| 1 - .../secondary/llvm/tools/llvm-config/BUILD.gn | 6 +- .../llvm/include/llvm/Config/config.h | 3 - utils/bazel/llvm_configs/config.h.cmake | 3 - 25 files changed, 12 insertions(+), 215 deletions(-) delete mode 100644 llvm/cmake/modules/FindTerminfo.cmake delete mode 100644 llvm/utils/gn/build/libs/terminfo/BUILD.gn delete mode 100644 llvm/utils/gn/build/libs/terminfo/enable.gni diff --git a/clang/cmake/caches/Fuchsia-stage2.cmake b/clang/cmake/caches/Fuchsia-stage2.cmake index d5546e20873b3..66e764968e85c 100644 --- a/clang/cmake/caches/Fuchsia-stage2.cmake +++ b/clang/cmake/caches/Fuchsia-stage2.cmake @@ -19,7 +19,6 @@ set(LLVM_ENABLE_LLD ON CACHE BOOL "") set(LLVM_ENABLE_LTO ON CACHE BOOL "") set(LLVM_ENABLE_PER_TARGET_RUNTIME_DIR ON CACHE BOOL "") set(LLVM_ENABLE_PLUGINS OFF CACHE BOOL "") -set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "") set(LLVM_ENABLE_UNWIND_TABLES OFF CACHE BOOL "") set(LLVM_ENABLE_Z3_SOLVER OFF CACHE BOOL "") set(LLVM_ENABLE_ZLIB ON CACHE BOOL "") diff --git a/clang/cmake/caches/Fuchsia.cmake b/clang/cmake/caches/Fuchsia.cmake index 30a3b9116a461..4d3af3ad3f403 100644 --- a/clang/cmake/caches/Fuchsia.cmake +++ b/clang/cmake/caches/Fuchsia.cmake @@ -12,7 +12,6 @@ set(LLVM_ENABLE_DIA_SDK OFF CACHE BOOL "") set(LLVM_ENABLE_LIBEDIT OFF CACHE BOOL "") set(LLVM_ENABLE_LIBXML2 OFF CACHE BOOL "") set(LLVM_ENABLE_PER_TARGET_RUNTIME_DIR ON CACHE BOOL "") -set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "") set(LLVM_ENABLE_UNWIND_TABLES OFF CACHE BOOL "") set(LLVM_ENABLE_Z3_SOLVER OFF CACHE BOOL "") set(LLVM_ENABLE_ZLIB OFF CACHE BOOL "") @@ -34,7 +33,6 @@ set(_FUCHSIA_BOOTSTRAP_PASSTHROUGH LibXml2_ROOT LLVM_ENABLE_CURL LLVM_ENABLE_HTTPLIB - LLVM_ENABLE_TERMINFO LLVM_ENABLE_LIBEDIT CURL_ROOT OpenSSL_ROOT @@ -47,11 +45,6 @@ set(_FUCHSIA_BOOTSTRAP_PASSTHROUGH CURSES_LIBRARIES PANEL_LIBRARIES - # Deprecated - Terminfo_ROOT - - Terminfo_LIBRARIES - # Deprecated LibEdit_ROOT diff --git a/clang/cmake/caches/VectorEngine.cmake b/clang/cmake/caches/VectorEngine.cmake index 2f968a21cc407..b429fb0997d7a 100644 --- a/clang/cmake/caches/VectorEngine.cmake +++ b/clang/cmake/caches/VectorEngine.cmake @@ -13,9 +13,7 @@ # ninja # -# Disable TERMINFO, ZLIB, and ZSTD for VE since there is no pre-compiled -# libraries. -set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "") +# Disable ZLIB, and ZSTD for VE since there is no pre-compiled libraries. set(LLVM_ENABLE_ZLIB OFF CACHE BOO
[Lldb-commits] [clang] [compiler-rt] [lldb] [llvm] [Support] Remove terminfo dependency (PR #92865)
llvmbot wrote: @llvm/pr-subscribers-lldb @llvm/pr-subscribers-clang Author: Aaron Siddhartha Mondal (aaronmondal) Changes The terminfo dependency introduces a significant nonhermeticity into the build. It doesn't respect `--no-undefined-version` meaning that it's not a dependency that can be built with Clang 17+. This forces maintainers of source-based distributions to implement patches or ignore linker errors. Remove it to reduce the closure size and improve portability of LLVM-based tools. Users can still use command line arguments to toggle color support expliticly. Fixes #75490 Closes #53294 #23355 --- Patch is 20.59 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/92865.diff 25 Files Affected: - (modified) clang/cmake/caches/Fuchsia-stage2.cmake (-1) - (modified) clang/cmake/caches/Fuchsia.cmake (-7) - (modified) clang/cmake/caches/VectorEngine.cmake (+1-3) - (modified) clang/utils/analyzer/entrypoint.py (+1-1) - (modified) compiler-rt/cmake/config-ix.cmake (-15) - (modified) compiler-rt/lib/sanitizer_common/symbolizer/scripts/build_symbolizer.sh (-1) - (modified) compiler-rt/lib/xray/tests/CMakeLists.txt (-5) - (modified) lldb/docs/resources/build.rst (-1) - (modified) lldb/source/Core/CMakeLists.txt (-3) - (modified) llvm/CMakeLists.txt (-2) - (modified) llvm/cmake/config-ix.cmake (-10) - (removed) llvm/cmake/modules/FindTerminfo.cmake (-55) - (modified) llvm/cmake/modules/LLVMConfig.cmake.in (-5) - (modified) llvm/docs/ReleaseNotes.rst (+4) - (modified) llvm/include/llvm/Config/config.h.cmake (-3) - (modified) llvm/lib/Support/CMakeLists.txt (-11) - (modified) llvm/lib/Support/Unix/Process.inc (+4-56) - (modified) llvm/utils/gn/README.rst (+1-1) - (removed) llvm/utils/gn/build/libs/terminfo/BUILD.gn (-12) - (removed) llvm/utils/gn/build/libs/terminfo/enable.gni (-4) - (modified) llvm/utils/gn/secondary/llvm/include/llvm/Config/BUILD.gn (-7) - (modified) llvm/utils/gn/secondary/llvm/lib/Support/BUILD.gn (-1) - (modified) llvm/utils/gn/secondary/llvm/tools/llvm-config/BUILD.gn (+1-5) - (modified) utils/bazel/llvm-project-overlay/llvm/include/llvm/Config/config.h (-3) - (modified) utils/bazel/llvm_configs/config.h.cmake (-3) ``diff diff --git a/clang/cmake/caches/Fuchsia-stage2.cmake b/clang/cmake/caches/Fuchsia-stage2.cmake index d5546e20873b3..66e764968e85c 100644 --- a/clang/cmake/caches/Fuchsia-stage2.cmake +++ b/clang/cmake/caches/Fuchsia-stage2.cmake @@ -19,7 +19,6 @@ set(LLVM_ENABLE_LLD ON CACHE BOOL "") set(LLVM_ENABLE_LTO ON CACHE BOOL "") set(LLVM_ENABLE_PER_TARGET_RUNTIME_DIR ON CACHE BOOL "") set(LLVM_ENABLE_PLUGINS OFF CACHE BOOL "") -set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "") set(LLVM_ENABLE_UNWIND_TABLES OFF CACHE BOOL "") set(LLVM_ENABLE_Z3_SOLVER OFF CACHE BOOL "") set(LLVM_ENABLE_ZLIB ON CACHE BOOL "") diff --git a/clang/cmake/caches/Fuchsia.cmake b/clang/cmake/caches/Fuchsia.cmake index 30a3b9116a461..4d3af3ad3f403 100644 --- a/clang/cmake/caches/Fuchsia.cmake +++ b/clang/cmake/caches/Fuchsia.cmake @@ -12,7 +12,6 @@ set(LLVM_ENABLE_DIA_SDK OFF CACHE BOOL "") set(LLVM_ENABLE_LIBEDIT OFF CACHE BOOL "") set(LLVM_ENABLE_LIBXML2 OFF CACHE BOOL "") set(LLVM_ENABLE_PER_TARGET_RUNTIME_DIR ON CACHE BOOL "") -set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "") set(LLVM_ENABLE_UNWIND_TABLES OFF CACHE BOOL "") set(LLVM_ENABLE_Z3_SOLVER OFF CACHE BOOL "") set(LLVM_ENABLE_ZLIB OFF CACHE BOOL "") @@ -34,7 +33,6 @@ set(_FUCHSIA_BOOTSTRAP_PASSTHROUGH LibXml2_ROOT LLVM_ENABLE_CURL LLVM_ENABLE_HTTPLIB - LLVM_ENABLE_TERMINFO LLVM_ENABLE_LIBEDIT CURL_ROOT OpenSSL_ROOT @@ -47,11 +45,6 @@ set(_FUCHSIA_BOOTSTRAP_PASSTHROUGH CURSES_LIBRARIES PANEL_LIBRARIES - # Deprecated - Terminfo_ROOT - - Terminfo_LIBRARIES - # Deprecated LibEdit_ROOT diff --git a/clang/cmake/caches/VectorEngine.cmake b/clang/cmake/caches/VectorEngine.cmake index 2f968a21cc407..b429fb0997d7a 100644 --- a/clang/cmake/caches/VectorEngine.cmake +++ b/clang/cmake/caches/VectorEngine.cmake @@ -13,9 +13,7 @@ # ninja # -# Disable TERMINFO, ZLIB, and ZSTD for VE since there is no pre-compiled -# libraries. -set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "") +# Disable ZLIB, and ZSTD for VE since there is no pre-compiled libraries. set(LLVM_ENABLE_ZLIB OFF CACHE BOOL "") set(LLVM_ENABLE_ZSTD OFF CACHE BOOL "") diff --git a/clang/utils/analyzer/entrypoint.py b/clang/utils/analyzer/entrypoint.py index ff877060bad69..4deb42db0a0b1 100644 --- a/clang/utils/analyzer/entrypoint.py +++ b/clang/utils/analyzer/entrypoint.py @@ -54,7 +54,7 @@ def is_cmake_needed(): "cmake -G Ninja -DCMAKE_BUILD_TYPE=Release " "-DCMAKE_INSTALL_PREFIX=/analyzer -DLLVM_TARGETS_TO_BUILD=X86 " '-DLLVM_ENABLE_PROJECTS="clang;openmp" -DLLVM_BUILD_RUNTIME=OFF ' -"-DLLVM_ENABLE_TERMINFO=OFF -DCLANG_ENABLE_ARCMT=OFF " +"-DCLANG_ENABLE_ARCMT=OFF " "-DCLANG_ENABLE_STATIC_ANALYZER=ON" ) diff --git a/compiler
[Lldb-commits] [lldb] SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` (PR #89868)
antmox wrote: Hi @royitaqi , This commit broke lldb-aarch64-windows buildbot : https://lab.llvm.org/buildbot/#/builders/219/builds/11564 Looks like callback_token_t is not defined for WIN32 in lldb-types.h Could you please look at this ? https://github.com/llvm/llvm-project/pull/89868 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits