[Lldb-commits] [lldb] [lldb] Correct invalid format style (PR #98089)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/98089 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Support throw and catch exception breakpoints for dynamica… (PR #97871)
https://github.com/walter-erquinigo updated https://github.com/llvm/llvm-project/pull/97871 >From aa2ad3b675f67581dde07a476725d2574fc6e7da Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Fri, 5 Jul 2024 20:30:44 -0400 Subject: [PATCH] [lldb-dap] Support throw and catch exception breakpoints for dynamically registered languages First of all, this is done to support exceptions for the Mojo language, but it's done in a way that will benefit any other plugin language. 1. I added a new lldb-dap CLI argument (not DAP field) called `pre-init-commands`. These commands are executed before DAP initialization. The other `init-commands` are executed after DAP initialization. It's worth mentioning that the debug adapter returns to VSCode the list of supported exception breakpoints during DAP initialization, which means that I need to register the Mojo plugin before that initialization step, hence the need for `pre-init-commands`. In general, language plugins should be registered in that step, as they affect the capabilities of the debugger. 2. I added a set of APIs for lldb-dap to query information of each language related to exception breakpoints. E.g. whether a language supports throw or catch breakpoints, how the throw keyword is called in each particular language, etc. 3. I'm realizing that the Swift support for exception breakpoints in lldb-dap should have been implemented in this way, instead of hardcoding it. --- lldb/include/lldb/API/SBLanguageRuntime.h | 26 +++ lldb/include/lldb/Target/Language.h | 8 lldb/source/API/SBLanguageRuntime.cpp | 40 + lldb/tools/lldb-dap/DAP.cpp | 54 ++- lldb/tools/lldb-dap/DAP.h | 2 + lldb/tools/lldb-dap/Options.td| 8 lldb/tools/lldb-dap/lldb-dap.cpp | 19 ++-- 7 files changed, 153 insertions(+), 4 deletions(-) diff --git a/lldb/include/lldb/API/SBLanguageRuntime.h b/lldb/include/lldb/API/SBLanguageRuntime.h index 38aac05d490c1..acdc256fa2ac5 100644 --- a/lldb/include/lldb/API/SBLanguageRuntime.h +++ b/lldb/include/lldb/API/SBLanguageRuntime.h @@ -18,6 +18,32 @@ class SBLanguageRuntime { static lldb::LanguageType GetLanguageTypeFromString(const char *string); static const char *GetNameForLanguageType(lldb::LanguageType language); + + /// Returns whether the given language is any version of C++. + static bool LanguageIsCPlusPlus(lldb::LanguageType language); + + /// Returns whether the given language is Obj-C or Obj-C++. + static bool LanguageIsObjC(lldb::LanguageType language); + + /// Returns whether the given language is any version of C, C++ or Obj-C. + static bool LanguageIsCFamily(lldb::LanguageType language); + + /// Returns whether the given language supports exception breakpoints on + /// throw statements. + static bool SupportsExceptionBreakpointsOnThrow(lldb::LanguageType language); + + /// Returns whether the given language supports exception breakpoints on + /// catch statements. + static bool SupportsExceptionBreakpointsOnCatch(lldb::LanguageType language); + + /// Returns the keyword used for throw statements in the given language, e.g. + /// Python uses \b raise. Returns \b nullptr if the language is not supported. + static const char *GetThrowKeywordForLanguage(lldb::LanguageType language); + + /// Returns the keyword used for catch statements in the given language, e.g. + /// Python uses \b except. Returns \b nullptr if the language is not + /// supported. + static const char *GetCatchKeywordForLanguage(lldb::LanguageType language); }; } // namespace lldb diff --git a/lldb/include/lldb/Target/Language.h b/lldb/include/lldb/Target/Language.h index 83bf7635e369a..41d8eeef469ea 100644 --- a/lldb/include/lldb/Target/Language.h +++ b/lldb/include/lldb/Target/Language.h @@ -371,6 +371,14 @@ class Language : public PluginInterface { /// a corresponding LanguageRuntime plugin. virtual bool SupportsExceptionBreakpointsOnCatch() const { return false; } + /// Returns the keyword used for throw statements in this language, e.g. + /// Python uses \b raise. Defaults to \b throw. + virtual llvm::StringRef GetThrowKeyword() const { return "throw"; } + + /// Returns the keyword used for catch statements in this language, e.g. + /// Python uses \b except. Defaults to \b catch. + virtual llvm::StringRef GetCatchKeyword() const { return "catch"; } + protected: // Classes that inherit from Language can see and modify these diff --git a/lldb/source/API/SBLanguageRuntime.cpp b/lldb/source/API/SBLanguageRuntime.cpp index d571f282fce03..8599c2598b9fb 100644 --- a/lldb/source/API/SBLanguageRuntime.cpp +++ b/lldb/source/API/SBLanguageRuntime.cpp @@ -26,3 +26,43 @@ SBLanguageRuntime::GetNameForLanguageType(lldb::LanguageType language) { return Language::GetNameForLanguageType(language); } + +bool SBLanguageRuntime::LanguageIsCPlusPlus(lldb::LanguageType language) { + return
[Lldb-commits] [lldb] [lldb-dap] Support throw and catch exception breakpoints for dynamica… (PR #97871)
@@ -58,10 +58,17 @@ DAP::DAP() DAP::~DAP() = default; +/// Return string with first character capitalized. +static std::string capitalize(llvm::StringRef str) { + if (str.empty()) +return ""; + return ((llvm::Twine)llvm::toUpper(str[0]) + str.drop_front()).str(); +} + void DAP::PopulateExceptionBreakpoints() { llvm::call_once(init_exception_breakpoints_flag, [this]() { exception_breakpoints = std::vector {}; - + walter-erquinigo wrote: This one doesn't affect git blame history. It should be fine :) https://github.com/llvm/llvm-project/pull/97871 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Support exception breakpoints for plugin-provided languages (PR #97675)
walter-erquinigo wrote: > Exception Breakpoints are created by the static method > LanguageRuntime::CreateExceptionBreakpoint. So they don't require a process. Indeed, but let me elaborate. What I need is a method that doesn't require a process that could tell me if a certain language can support exception breakpoints, as that's what the checks in the `breakpoint set -E ` command try to do. Then I had two main choices w.r.t `LanguageRuntime`: - Add the method as non-static `LanguageRuntime`, but `LanguageRuntime` instances do require a process. - Add a static method in `LanguageRuntime`, like `CreateExceptionBreakpoint`, but it turns out that `CreateExceptionBreakpoint` ends up relying on `Language::GetDefaultExceptionResolverDescription` and `Language::GetExceptionResolverDescription`. So this made me believe that it'd be better to place all the static exception feature bits in `Language` and not `LanguageRuntime`. `LanguageRuntime` seems to be a place more suited for dealing with runtime behaviors and not static pieces of information. > It's a little awkward to have a static method in LanguageRuntime that makes > the Exception breakpoint conditioned by a Language method > 'SupportsExceptionBreakpoint". I somewhat agree with it, but probably I'd end up writing a static method `LanguageRuntime::SupportsExceptionBreakpoint` that invokes a non-static `Language::SupportsExceptionBreakpoint`. And as I mentioned, there's already precedent for other exception related stuff in `Language`. https://github.com/llvm/llvm-project/pull/97675 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Support throw and catch exception breakpoints for dynamica… (PR #97871)
walter-erquinigo wrote: This is a screenshot of how it's looking for me on VSCode. ![image](https://github.com/llvm/llvm-project/assets/1613874/7a344b26-549c-4be6-b7d6-7082e701ee88) https://github.com/llvm/llvm-project/pull/97871 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Support throw and catch exception breakpoints for dynamica… (PR #97871)
https://github.com/walter-erquinigo created https://github.com/llvm/llvm-project/pull/97871 …lly registered languages First of all, this is done to support exceptions for the Mojo language, but it's done in a way that will benefit any other plugin language. 1. I added a new lldb-dap CLI argument (not DAP field) called `pre-init-commands`. These commands are executed before DAP initialization. The other `init-commands` are executed after DAP initialization. It's worth mentioning that the debug adapter returns to VSCode the list of supported exception breakpoints during DAP initialization, which means that I need to register the Mojo plugin before that initialization step, hence the need for `pre-init-commands`. In general, language plugins should be registered in that step, as they affect the capabilities of the debugger. 2. I added a set of APIs for lldb-dap to query information of each language related to exception breakpoints. E.g. whether a language supports throw or catch breakpoints, how the throw keyword is called in each particular language, etc. 3. I'm realizing that the Swift support for exception breakpoints in lldb-dap should have been implemented in this way, instead of hardcoding it. >From 63ab70e2a02faed8322c71dc2491428938891471 Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Fri, 5 Jul 2024 20:30:44 -0400 Subject: [PATCH] [lldb-dap] Support throw and catch exception breakpoints for dynamically registered languages First of all, this is done to support exceptions for the Mojo language, but it's done in a way that will benefit any other plugin language. 1. I added a new lldb-dap CLI argument (not DAP field) called `pre-init-commands`. These commands are executed before DAP initialization. The other `init-commands` are executed after DAP initialization. It's worth mentioning that the debug adapter returns to VSCode the list of supported exception breakpoints during DAP initialization, which means that I need to register the Mojo plugin before that initialization step, hence the need for `pre-init-commands`. In general, language plugins should be registered in that step, as they affect the capabilities of the debugger. 2. I added a set of APIs for lldb-dap to query information of each language related to exception breakpoints. E.g. whether a language supports throw or catch breakpoints, how the throw keyword is called in each particular language, etc. 3. I'm realizing that the Swift support for exception breakpoints in lldb-dap should have been implemented in this way, instead of hardcoding it. --- lldb/include/lldb/API/SBLanguageRuntime.h | 26 +++ lldb/include/lldb/Target/Language.h | 8 lldb/source/API/SBLanguageRuntime.cpp | 40 + lldb/tools/lldb-dap/DAP.cpp | 55 ++- lldb/tools/lldb-dap/DAP.h | 2 + lldb/tools/lldb-dap/Options.td| 8 lldb/tools/lldb-dap/lldb-dap.cpp | 19 ++-- 7 files changed, 154 insertions(+), 4 deletions(-) diff --git a/lldb/include/lldb/API/SBLanguageRuntime.h b/lldb/include/lldb/API/SBLanguageRuntime.h index 38aac05d490c1..acdc256fa2ac5 100644 --- a/lldb/include/lldb/API/SBLanguageRuntime.h +++ b/lldb/include/lldb/API/SBLanguageRuntime.h @@ -18,6 +18,32 @@ class SBLanguageRuntime { static lldb::LanguageType GetLanguageTypeFromString(const char *string); static const char *GetNameForLanguageType(lldb::LanguageType language); + + /// Returns whether the given language is any version of C++. + static bool LanguageIsCPlusPlus(lldb::LanguageType language); + + /// Returns whether the given language is Obj-C or Obj-C++. + static bool LanguageIsObjC(lldb::LanguageType language); + + /// Returns whether the given language is any version of C, C++ or Obj-C. + static bool LanguageIsCFamily(lldb::LanguageType language); + + /// Returns whether the given language supports exception breakpoints on + /// throw statements. + static bool SupportsExceptionBreakpointsOnThrow(lldb::LanguageType language); + + /// Returns whether the given language supports exception breakpoints on + /// catch statements. + static bool SupportsExceptionBreakpointsOnCatch(lldb::LanguageType language); + + /// Returns the keyword used for throw statements in the given language, e.g. + /// Python uses \b raise. Returns \b nullptr if the language is not supported. + static const char *GetThrowKeywordForLanguage(lldb::LanguageType language); + + /// Returns the keyword used for catch statements in the given language, e.g. + /// Python uses \b except. Returns \b nullptr if the language is not + /// supported. + static const char *GetCatchKeywordForLanguage(lldb::LanguageType language); }; } // namespace lldb diff --git a/lldb/include/lldb/Target/Language.h b/lldb/include/lldb/Target/Language.h index 83bf7635e369a..41d8eeef469ea 100644 --- a/lldb/include/lldb/Target/Language.h +++
[Lldb-commits] [lldb] 3bfc516 - [lldb-dap][NFC] Minor rename
Author: walter erquinigo Date: 2024-07-05T13:12:13-04:00 New Revision: 3bfc5167d9e49b9a53e364e8d8853fce543cca0f URL: https://github.com/llvm/llvm-project/commit/3bfc5167d9e49b9a53e364e8d8853fce543cca0f DIFF: https://github.com/llvm/llvm-project/commit/3bfc5167d9e49b9a53e364e8d8853fce543cca0f.diff LOG: [lldb-dap][NFC] Minor rename As a minor follow up for https://github.com/llvm/llvm-project/pull/97675, I'm renaming `SupportsExceptionBreakpoints` to `SupportsExceptionBreakpointsOnThrow` and adding a `SupportsExceptionBreakpointsOnCatch` to have a bit of more granularity. Added: Modified: lldb/include/lldb/Target/Language.h lldb/source/Commands/CommandObjectBreakpoint.cpp lldb/source/Plugins/Language/ObjC/ObjCLanguage.h Removed: diff --git a/lldb/include/lldb/Target/Language.h b/lldb/include/lldb/Target/Language.h index 2d6e5a40a0c0e4..83bf7635e369a5 100644 --- a/lldb/include/lldb/Target/Language.h +++ b/lldb/include/lldb/Target/Language.h @@ -363,9 +363,13 @@ class Language : public PluginInterface { return false; } - /// Returns true if this Language supports exception breakpoints via a - /// corresponding LanguageRuntime plugin. - virtual bool SupportsExceptionBreakpoints() const { return false; } + /// Returns true if this Language supports exception breakpoints on throw via + /// a corresponding LanguageRuntime plugin. + virtual bool SupportsExceptionBreakpointsOnThrow() const { return false; } + + /// Returns true if this Language supports exception breakpoints on catch via + /// a corresponding LanguageRuntime plugin. + virtual bool SupportsExceptionBreakpointsOnCatch() const { return false; } protected: // Classes that inherit from Language can see and modify these diff --git a/lldb/source/Commands/CommandObjectBreakpoint.cpp b/lldb/source/Commands/CommandObjectBreakpoint.cpp index a5fe9273fac76d..773f8ed2fa8af8 100644 --- a/lldb/source/Commands/CommandObjectBreakpoint.cpp +++ b/lldb/source/Commands/CommandObjectBreakpoint.cpp @@ -317,7 +317,8 @@ class CommandObjectBreakpointSet : public CommandObjectParsed { break; default: if (Language *languagePlugin = Language::FindPlugin(language)) { -if (languagePlugin->SupportsExceptionBreakpoints()) { +if (languagePlugin->SupportsExceptionBreakpointsOnThrow() || +languagePlugin->SupportsExceptionBreakpointsOnCatch()) { m_exception_language = language; break; } diff --git a/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h b/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h index a61d0f128370d4..d9c0cd3c18cfa1 100644 --- a/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h +++ b/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h @@ -194,7 +194,7 @@ class ObjCLanguage : public Language { llvm::StringRef GetInstanceVariableName() override { return "self"; } - bool SupportsExceptionBreakpoints() const override { return true; } + bool SupportsExceptionBreakpointsOnThrow() const override { return true; } // PluginInterface protocol llvm::StringRef GetPluginName() override { return GetPluginNameStatic(); } ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Support exception breakpoints for plugin-provided languages (PR #97675)
https://github.com/walter-erquinigo closed https://github.com/llvm/llvm-project/pull/97675 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Support exception breakpoints for plugin-provided languages (PR #97675)
walter-erquinigo wrote: > And does this list include languages that are not plugin provided? The hardcoded list in the file being changes includes C++ and Objc in its various variants. > I was wondering why only Objective C changed, but if the rest are not plugins > then this makes sense. That was the only simple example I could use to show how this change does work. Thanks for the review! https://github.com/llvm/llvm-project/pull/97675 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Support exception breakpoints for plugin-provided languages (PR #97675)
@@ -319,6 +316,12 @@ class CommandObjectBreakpointSet : public CommandObjectParsed { error_context = "Unknown language type for exception breakpoint"; break; default: + if (Language *languagePlugin = Language::FindPlugin(language)) { walter-erquinigo wrote: Within switch statements I tend to be very paranoid with braces https://github.com/llvm/llvm-project/pull/97675 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Support exception breakpoints for plugin-provided languages (PR #97675)
https://github.com/walter-erquinigo updated https://github.com/llvm/llvm-project/pull/97675 >From 5d1a7254d1e1a541a7b901be0d3a84eab42474b2 Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Thu, 4 Jul 2024 00:34:14 -0400 Subject: [PATCH 1/2] [LLDB] Support exception breakpoints for plugin-provided languages CommandObjectBreakpoint has a harcoded list of languages for which exception breakpoints can be enabled. I'm making this a bit more generic so that my Mojo plugin can get this feature. Basically, I'm adding a new overridable method `Language::SupportsExceptionBreakpoints` that can be used by language plugins to determine whether they support this feature or not. This method is used in addition to the hardcoded list and, as an example, I'm using it for the ObjC language support. Another route is simply to avoid doing the check that it's being done right now and simply try to the create the exception breakpoint for whatever language that is not in the hardcoded list. I'm happy to do that if the reviewers think it's a good idea. As a note, the other possible place for adding this `SupportsExceptionBreakpoints` method is in `LanguageRuntime`. However, accessing it requires having a process, which is not always the case when invoking the `breakpoint set -E` command. The process might not be alive yet, so `Language` is a good second place for this. And as a final note, I don't want to make this `SupportsExceptionBreakpoints` complicated. I'm keeping it as simple as possible because it can easily evolve as it's not part of the public API. --- lldb/include/lldb/Target/Language.h | 6 +- lldb/source/Commands/CommandObjectBreakpoint.cpp | 9 ++--- lldb/source/Plugins/Language/ObjC/ObjCLanguage.h | 2 ++ 3 files changed, 13 insertions(+), 4 deletions(-) diff --git a/lldb/include/lldb/Target/Language.h b/lldb/include/lldb/Target/Language.h index ff7c60bf68bfc..9c2c765ce497f 100644 --- a/lldb/include/lldb/Target/Language.h +++ b/lldb/include/lldb/Target/Language.h @@ -245,7 +245,7 @@ class Language : public PluginInterface { // a match. But we wouldn't want this to match AnotherA::my_function. The // user is specifying a truncated path, not a truncated set of characters. // This function does a language-aware comparison for those purposes. - virtual bool DemangledNameContainsPath(llvm::StringRef path, + virtual bool DemangledNameContainsPath(llvm::StringRef path, ConstString demangled) const; // if a language has a custom format for printing variable declarations that @@ -363,6 +363,10 @@ class Language : public PluginInterface { return false; } + /// Returns true if this Language supports exception breakpoints via a + /// corresponding LanguageRuntime plugin. + virtual bool SupportsExceptionBreakpoints() const { return false; } + protected: // Classes that inherit from Language can see and modify these diff --git a/lldb/source/Commands/CommandObjectBreakpoint.cpp b/lldb/source/Commands/CommandObjectBreakpoint.cpp index cd4c7790f447e..a5fe9273fac76 100644 --- a/lldb/source/Commands/CommandObjectBreakpoint.cpp +++ b/lldb/source/Commands/CommandObjectBreakpoint.cpp @@ -308,9 +308,6 @@ class CommandObjectBreakpointSet : public CommandObjectParsed { case eLanguageTypeC_plus_plus_14: m_exception_language = eLanguageTypeC_plus_plus; break; -case eLanguageTypeObjC: - m_exception_language = eLanguageTypeObjC; - break; case eLanguageTypeObjC_plus_plus: error_context = "Set exception breakpoints separately for c++ and objective-c"; @@ -319,6 +316,12 @@ class CommandObjectBreakpointSet : public CommandObjectParsed { error_context = "Unknown language type for exception breakpoint"; break; default: + if (Language *languagePlugin = Language::FindPlugin(language)) { +if (languagePlugin->SupportsExceptionBreakpoints()) { + m_exception_language = language; + break; +} + } error_context = "Unsupported language type for exception breakpoint"; } if (!error_context.empty()) diff --git a/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h b/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h index a50f4b036108d..a61d0f128370d 100644 --- a/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h +++ b/lldb/source/Plugins/Language/ObjC/ObjCLanguage.h @@ -194,6 +194,8 @@ class ObjCLanguage : public Language { llvm::StringRef GetInstanceVariableName() override { return "self"; } + bool SupportsExceptionBreakpoints() const override { return true; } + // PluginInterface protocol llvm::StringRef GetPluginName() override { return GetPluginNameStatic(); } }; >From e99702d0cafaaa87e06a845e3f3e14868f9e800b Mon Sep 17 00:00:00 2001 From: Walter Erquinigo Date: Thu, 4 Jul 2024 10:02:45 -0400
[Lldb-commits] [lldb] [LLDB] Support exception breakpoints for plugin-provided languages (PR #97675)
https://github.com/walter-erquinigo created https://github.com/llvm/llvm-project/pull/97675 CommandObjectBreakpoint has a harcoded list of languages for which exception breakpoints can be enabled. I'm making this a bit more generic so that my Mojo plugin can get this feature. Basically, I'm adding a new overridable method `Language::SupportsExceptionBreakpoints` that can be used by language plugins to determine whether they support this feature or not. This method is used in addition to the hardcoded list and, as an example, I'm using it for the ObjC language support. Another route is simply to avoid doing the check that it's being done right now and simply try to the create the exception breakpoint for whatever language that is not in the hardcoded list. I'm happy to do that if the reviewers think it's a good idea. As a note, the other possible place for adding this `SupportsExceptionBreakpoints` method is in `LanguageRuntime`. However, accessing it requires having a process, which is not always the case when invoking the `breakpoint set -E` command. The process might not be alive yet, so `Language` is a good second place for this. And as a final note, I don't want to make this `SupportsExceptionBreakpoints` complicated. I'm keeping it as simple as possible because it can easily evolve as it's not part of the public API. >From 5d1a7254d1e1a541a7b901be0d3a84eab42474b2 Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Thu, 4 Jul 2024 00:34:14 -0400 Subject: [PATCH] [LLDB] Support exception breakpoints for plugin-provided languages CommandObjectBreakpoint has a harcoded list of languages for which exception breakpoints can be enabled. I'm making this a bit more generic so that my Mojo plugin can get this feature. Basically, I'm adding a new overridable method `Language::SupportsExceptionBreakpoints` that can be used by language plugins to determine whether they support this feature or not. This method is used in addition to the hardcoded list and, as an example, I'm using it for the ObjC language support. Another route is simply to avoid doing the check that it's being done right now and simply try to the create the exception breakpoint for whatever language that is not in the hardcoded list. I'm happy to do that if the reviewers think it's a good idea. As a note, the other possible place for adding this `SupportsExceptionBreakpoints` method is in `LanguageRuntime`. However, accessing it requires having a process, which is not always the case when invoking the `breakpoint set -E` command. The process might not be alive yet, so `Language` is a good second place for this. And as a final note, I don't want to make this `SupportsExceptionBreakpoints` complicated. I'm keeping it as simple as possible because it can easily evolve as it's not part of the public API. --- lldb/include/lldb/Target/Language.h | 6 +- lldb/source/Commands/CommandObjectBreakpoint.cpp | 9 ++--- lldb/source/Plugins/Language/ObjC/ObjCLanguage.h | 2 ++ 3 files changed, 13 insertions(+), 4 deletions(-) diff --git a/lldb/include/lldb/Target/Language.h b/lldb/include/lldb/Target/Language.h index ff7c60bf68bfc..9c2c765ce497f 100644 --- a/lldb/include/lldb/Target/Language.h +++ b/lldb/include/lldb/Target/Language.h @@ -245,7 +245,7 @@ class Language : public PluginInterface { // a match. But we wouldn't want this to match AnotherA::my_function. The // user is specifying a truncated path, not a truncated set of characters. // This function does a language-aware comparison for those purposes. - virtual bool DemangledNameContainsPath(llvm::StringRef path, + virtual bool DemangledNameContainsPath(llvm::StringRef path, ConstString demangled) const; // if a language has a custom format for printing variable declarations that @@ -363,6 +363,10 @@ class Language : public PluginInterface { return false; } + /// Returns true if this Language supports exception breakpoints via a + /// corresponding LanguageRuntime plugin. + virtual bool SupportsExceptionBreakpoints() const { return false; } + protected: // Classes that inherit from Language can see and modify these diff --git a/lldb/source/Commands/CommandObjectBreakpoint.cpp b/lldb/source/Commands/CommandObjectBreakpoint.cpp index cd4c7790f447e..a5fe9273fac76 100644 --- a/lldb/source/Commands/CommandObjectBreakpoint.cpp +++ b/lldb/source/Commands/CommandObjectBreakpoint.cpp @@ -308,9 +308,6 @@ class CommandObjectBreakpointSet : public CommandObjectParsed { case eLanguageTypeC_plus_plus_14: m_exception_language = eLanguageTypeC_plus_plus; break; -case eLanguageTypeObjC: - m_exception_language = eLanguageTypeObjC; - break; case eLanguageTypeObjC_plus_plus: error_context = "Set exception breakpoints separately for c++ and objective-c"; @@ -319,6 +316,12 @@ class
[Lldb-commits] [lldb] [LLDB] Add AST node classes, functions, etc. for Data Inspection Lang… (PR #95738)
walter-erquinigo wrote: I second everything that Pavel says. I think this would be the best approach. The existing frame var implementation is not that "smart", so it should be practical to fully replace it with the new DIL in its first stage. An additional consideration is that lldb-dap, which is being more and more frequently used, relies on `frame var` for executing most expressions. `expr` is just a fallback. Therefore, replacing `frame var` with DIL right away has the benefit of getting tested right away by all the lldb-dap users. https://github.com/llvm/llvm-project/pull/95738 ___ 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/walter-erquinigo approved this pull request. This LGTM 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)
walter-erquinigo wrote: I'll review this today or tomorrow. Thanks for all the activity! 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] Fix flaky TestDAP_console test. (PR #94494)
walter-erquinigo wrote: @mbucko , could you request commit access to Chris Latner? ``` We grant commit access to contributors with a track record of submitting high quality patches. If you would like commit access, please send an email to [Chris](mailto:clattner%40llvm.org) with your GitHub username. ``` That would be very helpful in case you break the build bots and want to push a hot fix. https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
@@ -337,7 +337,7 @@ def test_commands(self): # Get output from the console. This should contain both the # "exitCommands" that were run after the second breakpoint was hit # and the "terminateCommands" due to the debugging session ending -output = self.collect_console(duration=1.0) +output = self.collect_console(timeout_secs=1.0) walter-erquinigo wrote: add `terminateCommands` to the pattern https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
@@ -235,5 +235,5 @@ def test_terminate_commands(self): # Once it's disconnected the console should contain the # "terminateCommands" self.dap_server.request_disconnect(terminateDebuggee=True) -output = self.collect_console(duration=1.0) +output = self.collect_console(timeout_secs=1.0) walter-erquinigo wrote: add `terminateCommands` to the pattern https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
@@ -200,7 +200,7 @@ def test_commands(self): # Get output from the console. This should contain both the # "exitCommands" that were run after the second breakpoint was hit # and the "terminateCommands" due to the debugging session ending -output = self.collect_console(duration=1.0) +output = self.collect_console(timeout_secs=1.0) walter-erquinigo wrote: add `terminateCommands` to the pattern https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
@@ -47,7 +47,7 @@ def do_test_abort_on_error( postRunCommands=commands if use_post_run_commands else None, expectFailure=True, ) -full_output = self.collect_console(duration=1.0) +full_output = self.collect_console(timeout_secs=1.0) walter-erquinigo wrote: add `settings` to the pattern https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
@@ -75,6 +75,6 @@ def test_command_directive_abort_on_error_attach_commands(self): attachCommands=["?!" + command_quiet, "!" + command_abort_on_error], expectFailure=True, ) -full_output = self.collect_console(duration=1.0) +full_output = self.collect_console(timeout_secs=1.0) walter-erquinigo wrote: add `settings` to the pattern https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
@@ -467,5 +467,5 @@ def test_terminate_commands(self): # Once it's disconnected the console should contain the # "terminateCommands" self.dap_server.request_disconnect(terminateDebuggee=True) -output = self.collect_console(duration=1.0) +output = self.collect_console(timeout_secs=1.0) walter-erquinigo wrote: add `terminateCommands` to the pattern https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
walter-erquinigo wrote: Jonas' suggestion is pretty good. Please do that. Probably something like this would work ` def collect_console(timeout_secs=10, check_interval_secs=1): ... ` Then you can just update every caller of this function to just do `collect_console()` https://github.com/llvm/llvm-project/pull/94494 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix flaky TestDAP_console test. (PR #94494)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/94494 ___ 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,142 @@ +""" +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 +import socket + + +class TestDAP_attachByPortNum(lldbdap_testcase.DAPTestCaseBase): +def get_free_port(self): +s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) +s.bind(("", 0)) +port = s.getsockname()[1] +s.close() +return port + +def runTargetProgramOnPort(self, port=None, program=None): +server_tool = self.getBuiltinServerToolWithPortArg(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 +@skipIfRemote +def test_by_port(self): +""" +Tests attaching to a process by port. +""" +self.build_and_create_debug_adaptor() +program = self.getBuildArtifact("a.out") + +port = self.get_free_port() +self.process = self.runTargetProgramOnPort(port=port, program=program) +pid = self.process.pid +response = self.attach(program=program, port=port, sourceInitFile=True) +self.set_and_hit_breakpoint(continueToExit=True) +self.process.kill() + +@skipIfWindows +@skipIfNetBSD +@skipIfRemote +def test_by_port_and_pid(self): +""" +Tests attaching to a process by process ID and port number. +""" +self.build_and_create_debug_adaptor() +program = self.getBuildArtifact("a.out") + +port = self.get_free_port() +self.process = self.runTargetProgramOnPort(port=port, program=program) +pid = self.process.pid +response = self.attach( +program=program, +pid=pid, +port=port, +sourceInitFile=True, +expectFailure=True, +) +if not (response and response["success"]): +self.assertFalse( +response["success"], "The user can't specify both pid and port" +) +self.process.kill() + +@skipIfWindows +@skipIfNetBSD +@skipIfRemote walter-erquinigo wrote: you don't need `@skipIfRemote` anymore 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)
@@ -749,9 +752,30 @@ void request_attach(const llvm::json::Object ) { // Disable async events so the attach will be successful when we return from // the launch call and the launch will happen synchronously g_dap.debugger.SetAsync(false); -if (core_file.empty()) - g_dap.target.Attach(attach_info, error); -else +if (core_file.empty()) { + if ((pid != LLDB_INVALID_PROCESS_ID) && (port != invalid_port)) { +// If both pid and port numbers are specified. +error.SetErrorString("The user can't specify both pid and port"); + } else if (port != invalid_port) { +// If port is specified and pid is not. +lldb::SBListener listener = g_dap.debugger.GetListener(); + +// If the user hasn't provided the hostname property, default localhost +// being used. +std::string connect_url("connect://localhost:"); + +// If the user has provided hostname other than localhost. +if (!hostname.empty() && !hostname.starts_with("localhost")) { walter-erquinigo wrote: wouldn't it just work with `localhost` being passed to `llvm::formatv`? 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] Add timestamps to protocol logs (PR #93540)
https://github.com/walter-erquinigo approved this pull request. sounds good then! https://github.com/llvm/llvm-project/pull/93540 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Add timestamps to protocol logs (PR #93540)
@@ -103,7 +103,9 @@ void DAP::SendJSON(const llvm::json::Value ) { SendJSON(json_str); if (log) { -*log << "<-- " << std::endl +auto now = std::chrono::duration( +std::chrono::system_clock::now().time_since_epoch()); walter-erquinigo wrote: wouldn't it be better to use steady_clock? that's more stable for benchmarking https://github.com/llvm/llvm-project/pull/93540 ___ 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 call GetNumChildren on non-indexed synthetic variables (PR #93534)
https://github.com/walter-erquinigo approved this pull request. Thanks for doing this. Btw, that was a clever way of testing this functionality. https://github.com/llvm/llvm-project/pull/93534 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Fixed the TestDebuggerAPI test on x86_64 Windows host (PR #90580)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/90580 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Change GetChildCompilerTypeAtIndex to return Expected (NFC) (PR #92979)
https://github.com/walter-erquinigo approved this pull request. Pretty nice! This will be useful for Mojo as well https://github.com/llvm/llvm-project/pull/92979 ___ 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] [lldb-dap] Added "port" property to vscode "attach" command. (PR #91570)
walter-erquinigo wrote: Thanks, @labath , for chiming in. I actually agree with all your points. 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] Updating VariableDescription to use GetDescription() as a fallback. (PR #77026)
walter-erquinigo wrote: I'm okay with anything that ensures hovering is fast. https://github.com/llvm/llvm-project/pull/77026 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Fixed the DAP tests in case of a remote target (PR #92416)
walter-erquinigo wrote: That's a great idea. There's no such `dap` category at the moment, but it would be nice if such category is created as part of the ongoing lldb-dap test fixes. https://github.com/llvm/llvm-project/pull/92416 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Separate user and developer documentation (PR #92428)
https://github.com/walter-erquinigo approved this pull request. beautiful https://github.com/llvm/llvm-project/pull/92428 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Fixed the DAP tests in case of a remote target (PR #92416)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/92416 ___ 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 +@skipIfRemote +def test_by_port(self): +""" +Tests attaching to a process by port. +""" +self.build_and_create_debug_adaptor() +program = self.getBuildArtifact("a.out") + +port = "2345" +self.process = self.runTargetProgramOnPort(port=port, program=program) +pid = self.process.pid +response = self.attach(program=program, port=int(port), sourceInitFile=True) +self.set_and_hit_breakpoint(continueToExit=True) +self.process.kill() + +@skipIfWindows +@skipIfNetBSD # Hangs on NetBSD as well +@skipIfRemote +def test_by_port_and_pid(self): +""" +Tests attaching to a process by process ID and port number. +""" +self.build_and_create_debug_adaptor() +program = self.getBuildArtifact("a.out") + +port = "2345" walter-erquinigo wrote: use a different port for each test, just in case the test runner executes them simultaneously 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)
@@ -676,6 +676,8 @@ void request_attach(const llvm::json::Object ) { auto arguments = request.getObject("arguments"); const lldb::pid_t pid = GetUnsigned(arguments, "pid", LLDB_INVALID_PROCESS_ID); + const auto port = GetUnsigned(arguments, "port", LLDB_INVALID_PORT_NUMBER); + llvm::StringRef hostname = GetString(arguments, "hostname"); walter-erquinigo wrote: you can here set the default to "localhost", which will simplify the logic below 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)
@@ -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 "" walter-erquinigo wrote: return None instead of an empty string 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 + " " walter-erquinigo wrote: could you move the logic that finds automatically the path to lldb-server or debugserver to lldbdap_testcase? This logic seems to be useful to reuse 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 walter-erquinigo wrote: This "as well" looks weird. Did you test it there in fact? 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] Fixed the DAP tests in case of a remote target (PR #92398)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/92398 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Fixed an invalid error message in the DAP disconnect response (PR #92345)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/92345 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Support publishing to the VSCode market place (PR #92320)
https://github.com/walter-erquinigo approved this pull request. lgtm! https://github.com/llvm/llvm-project/pull/92320 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Include npm install in the extension installation steps (PR #92028)
https://github.com/walter-erquinigo closed https://github.com/llvm/llvm-project/pull/92028 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Updating VariableDescription to use GetDescription() as a fallback. (PR #77026)
walter-erquinigo wrote: I don't think anything has changed on VSCode proper. I've just verified I have the same experience as you. Given what you said, I'm in favor of reverting this or at least gating this feature under a json initialization option until the original author can look at this. https://github.com/llvm/llvm-project/pull/77026 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Correctly detect alias commands with arguments in repl (PR #92137)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/92137 ___ 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)
@@ -762,9 +765,31 @@ void request_attach(const llvm::json::Object ) { // Disable async events so the attach will be successful when we return from // the launch call and the launch will happen synchronously g_dap.debugger.SetAsync(false); -if (core_file.empty()) - g_dap.target.Attach(attach_info, error); -else +if (core_file.empty()) { + if ((pid != LLDB_INVALID_PROCESS_ID) && + (port != LLDB_INVALID_PORT_NUMBER)) { +// If both pid and port numbers are specified. +error.SetErrorString("The user can't specify both pid and port"); + } else if ((port != LLDB_INVALID_PORT_NUMBER) && (port < UINT16_MAX)) { walter-erquinigo wrote: Remove `(port < UINT16_MAX)` so that we get a meaningful error from the connection logic. 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)
@@ -335,6 +335,37 @@ def cleanup(): response["success"], "attach failed (%s)" % (response["message"]) ) +def attach_by_port( walter-erquinigo wrote: could you just extend the `def attach` function? Having a totally new entry point just adds more maintainance burden when doing refactors. 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,137 @@ +""" +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 +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 = "lldb-server" walter-erquinigo wrote: lldb-server is available on linux, and gdbserver on mac, so you need to look for both depending on the situation. @JDevlieghere , is there an SB API that we could use to get the path to the gdb-server that LLDB uses? 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] Include npm install in the extension installation steps (PR #92028)
https://github.com/walter-erquinigo created https://github.com/llvm/llvm-project/pull/92028 Otherwise the build step fails due to missing dependencies. >From b065234db18dd726b4e39a98ac0c360e052fe438 Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Mon, 13 May 2024 22:39:47 +0200 Subject: [PATCH] [lldb-dap] Include npm install in the extension installation steps Otherwise the build step fails due to missing dependencies. --- lldb/tools/lldb-dap/README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lldb/tools/lldb-dap/README.md b/lldb/tools/lldb-dap/README.md index 274b1519208a1..16ce4672be71c 100644 --- a/lldb/tools/lldb-dap/README.md +++ b/lldb/tools/lldb-dap/README.md @@ -46,6 +46,7 @@ Installing the plug-in is very straightforward and involves just a few steps. ```bash cd /path/to/lldb/tools/lldb-dap +npm install npm run package # This also compiles the extension. npm run vscode-install ``` @@ -69,6 +70,7 @@ no effect. ```bash # Bump version in package.json cd /path/to/lldb/tools/lldb-dap +npm install npm run package npm run vscode-install ``` ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb] Allow env override for LLDB_ARGDUMPER_PATH (PR #91688)
https://github.com/walter-erquinigo approved this pull request. lgtm https://github.com/llvm/llvm-project/pull/91688 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Fix a race during shutdown (PR #91591)
https://github.com/walter-erquinigo approved this pull request. This all makes sense to me. Thank you! https://github.com/llvm/llvm-project/pull/91591 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix dap variable value format issue (PR #90799)
walter-erquinigo wrote: I thought you were meaning UI changes via the fblldb extension, but if you are modying your fork of VSCode, there's nothing to be done then. https://github.com/llvm/llvm-project/pull/90799 ___ 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 fail when SBProcess::GetMemoryRegionInfo returns error. (PR #87649)
https://github.com/walter-erquinigo approved this pull request. makes sense to me https://github.com/llvm/llvm-project/pull/87649 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Fix dap variable value format issue (PR #90799)
https://github.com/walter-erquinigo approved this pull request. lgtm. It would be nice if new UI features could be added in the typescript code of lldb-dap, so that all users benefit from them. https://github.com/llvm/llvm-project/pull/90799 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Fix test_exit_status_message_sigterm test. (PR #90223)
walter-erquinigo wrote: @JDevlieghere , do you know if it's possible to add python dependencies somewhere for lldb tests? https://github.com/llvm/llvm-project/pull/90223 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Fix test_exit_status_message_sigterm test. (PR #90223)
walter-erquinigo wrote: What about trying to use a python builtin like https://docs.python.org/3/library/multiprocessing.html#multiprocessing.active_children? https://github.com/llvm/llvm-project/pull/90223 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][dap] always add column field in StackFrame body (PR #73393)
walter-erquinigo wrote: @semensanyok, I've just merged this PR because it's very straightforward. If it breaks the buildbots, I'll just revert it and let the original author fix it. https://github.com/llvm/llvm-project/pull/73393 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][dap] always add column field in StackFrame body (PR #73393)
https://github.com/walter-erquinigo closed https://github.com/llvm/llvm-project/pull/73393 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb-dap] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
https://github.com/walter-erquinigo edited https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
https://github.com/walter-erquinigo approved this pull request. lgtm. Thank you! I've wanted this feature for a while, tbh, because the user doesn't know if the program terminated successfully or if the debugger crashed. https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
@@ -4,10 +4,30 @@ import dap_server import lldbdap_testcase +import psutil +from collections import deque from lldbsuite.test import lldbutil from lldbsuite.test.decorators import * from lldbsuite.test.lldbtest import * +def get_subprocess_pid(process_name): +queue = deque([psutil.Process(os.getpid())]) +while queue: +process = queue.popleft() +if process.name() == process_name: +return process.pid +queue.extend(process.children()) walter-erquinigo wrote: this is a bit of an overkill, but it's correct anyway, so I'm okay with it https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
@@ -104,3 +124,27 @@ def test_empty_escape_prefix(self): "Help can be invoked", command_escape_prefix="", ) + +@skipIfWindows +@skipIfRemote +def test_exit_status_message(self): +source = "main.cpp" +program = self.getBuildArtifact("a.out") +self.build_and_launch(program, commandEscapePrefix="") +breakpoint1_line = line_number(source, "// breakpoint 1") +breakpoint_ids = self.set_source_breakpoints(source, [breakpoint1_line]) +self.continue_to_breakpoints(breakpoint_ids) + +# Kill lldb-server process. +process_name = "lldb-server" walter-erquinigo wrote: on mac, the process is called debugserver, so you need something like proces_name = "debugserver" if platform.platform() == "MacOS" else "lldb-server" https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
@@ -4,10 +4,30 @@ import dap_server import lldbdap_testcase +import psutil +from collections import deque from lldbsuite.test import lldbutil from lldbsuite.test.decorators import * from lldbsuite.test.lldbtest import * +def get_subprocess_pid(process_name): +queue = deque([psutil.Process(os.getpid())]) +while queue: +process = queue.popleft() +if process.name() == process_name: +return process.pid +queue.extend(process.children()) + +print(f"No subprocess with name {process_name} found", flush=True, file=sys.stderr) +return None walter-erquinigo wrote: this should be an assert that makes the test fail right away, because that child has to exist https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
@@ -104,3 +124,27 @@ def test_empty_escape_prefix(self): "Help can be invoked", command_escape_prefix="", ) + +@skipIfWindows +@skipIfRemote +def test_exit_status_message(self): +source = "main.cpp" +program = self.getBuildArtifact("a.out") +self.build_and_launch(program, commandEscapePrefix="") +breakpoint1_line = line_number(source, "// breakpoint 1") +breakpoint_ids = self.set_source_breakpoints(source, [breakpoint1_line]) +self.continue_to_breakpoints(breakpoint_ids) + +# Kill lldb-server process. +process_name = "lldb-server" +pid = get_subprocess_pid(process_name) +killProcess(pid, process_name) +# Get the console output +console_output = self.collect_console(1.0) + +# Verify the exit status message is printed. +self.assertIn( +"exited with status = -1 (0x) debugserver died with signal SIGTERM", +console_output, +"Exit status does not contain message 'exited with status'" +) walter-erquinigo wrote: could you also add another test in which a successful exit (i.e. exit code = 0) is printed as well? https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
@@ -4,10 +4,30 @@ import dap_server import lldbdap_testcase +import psutil +from collections import deque from lldbsuite.test import lldbutil from lldbsuite.test.decorators import * from lldbsuite.test.lldbtest import * +def get_subprocess_pid(process_name): +queue = deque([psutil.Process(os.getpid())]) +while queue: +process = queue.popleft() +if process.name() == process_name: +return process.pid +queue.extend(process.children()) + +print(f"No subprocess with name {process_name} found", flush=True, file=sys.stderr) +return None + +def killProcess(pid, process_name): +process = psutil.Process(pid) +process.terminate() +try: +process.wait(timeout=5) +except psutil.TimeoutExpired: +self.assertTrue(False, process_name + " process should have exited by now") walter-erquinigo wrote: you don't need an assert here if you want the test to fail, you can just let the exception bubble up https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
@@ -104,3 +127,27 @@ def test_empty_escape_prefix(self): "Help can be invoked", command_escape_prefix="", ) + +@skipIfWindows +@skipIfRemote +def test_exit_status_message(self): +source = "main.cpp" +program = self.getBuildArtifact("a.out") +self.build_and_launch(program, commandEscapePrefix="") +breakpoint1_line = line_number(source, "// breakpoint 1") +breakpoint_ids = self.set_source_breakpoints(source, [breakpoint1_line]) +self.continue_to_breakpoints(breakpoint_ids) + +# Kill lldb-server process. +process_name = "lldb-server" walter-erquinigo wrote: this is error prone because multiple lldb-servers might be running at the same time. You need the lldb-server or debugserver that is child of the current lldb-vscode process and not the most recent one https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
https://github.com/walter-erquinigo requested changes to this pull request. https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
https://github.com/walter-erquinigo edited https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Report exit status message in lldb-dap, same as lldb cli (PR #89405)
walter-erquinigo wrote: Yep, please write a python test. A possible idea is to have a target that does nothing for 10 seconds, during which you kill the debug server (lldb-server or debugserver) and then you assert on the final message sent by lldb-vscode. https://github.com/llvm/llvm-project/pull/89405 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][lldb-dap] Cleanup breakpoint filters. (PR #87550)
@@ -36,9 +36,7 @@ DAP::DAP() {{"cpp_catch", "C++ Catch", lldb::eLanguageTypeC_plus_plus}, {"cpp_throw", "C++ Throw", lldb::eLanguageTypeC_plus_plus}, {"objc_catch", "Objective-C Catch", lldb::eLanguageTypeObjC}, - {"objc_throw", "Objective-C Throw", lldb::eLanguageTypeObjC}, - {"swift_catch", "Swift Catch", lldb::eLanguageTypeSwift}, - {"swift_throw", "Swift Throw", lldb::eLanguageTypeSwift}}), + {"objc_throw", "Objective-C Throw", lldb::eLanguageTypeObjC}}), walter-erquinigo wrote: Btw, it's possible to register typesystems/languages at initialization via runtime plugins. I think it would be ideal if the breakpoint list could get updated/refreshed after the target has been loaded (maybe at the first stop point) https://github.com/llvm/llvm-project/pull/87550 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Initial step in targets DAP support (PR #86623)
@@ -3180,14 +3180,159 @@ void request_stepIn(const llvm::json::Object ) { llvm::json::Object response; FillResponse(request, response); auto arguments = request.getObject("arguments"); + + std::string step_in_target; + uint64_t target_id = GetUnsigned(arguments, "targetId", 0); + auto it = g_dap.step_in_targets.find(target_id); + if (it != g_dap.step_in_targets.end()) +step_in_target = it->second; + + const bool single_thread = GetBoolean(arguments, "singleThread", false); + lldb::RunMode run_mode = + single_thread ? lldb::eOnlyThisThread : lldb::eOnlyDuringStepping; lldb::SBThread thread = g_dap.GetLLDBThread(*arguments); if (thread.IsValid()) { // Remember the thread ID that caused the resume so we can set the // "threadCausedFocus" boolean value in the "stopped" events. g_dap.focus_tid = thread.GetThreadID(); -thread.StepInto(); +thread.StepInto(step_in_target.c_str(), run_mode); + } else { +response["success"] = llvm::json::Value(false); + } + g_dap.SendJSON(llvm::json::Value(std::move(response))); +} + +// "StepInTargetsRequest": { +// "allOf": [ { "$ref": "#/definitions/Request" }, { +// "type": "object", +// "description": "This request retrieves the possible step-in targets for +// the specified stack frame.\nThese targets can be used in the `stepIn` +// request.\nClients should only call this request if the corresponding +// capability `supportsStepInTargetsRequest` is true.", "properties": { +// "command": { +// "type": "string", +// "enum": [ "stepInTargets" ] +// }, +// "arguments": { +// "$ref": "#/definitions/StepInTargetsArguments" +// } +// }, +// "required": [ "command", "arguments" ] +// }] +// }, +// "StepInTargetsArguments": { +// "type": "object", +// "description": "Arguments for `stepInTargets` request.", +// "properties": { +// "frameId": { +// "type": "integer", +// "description": "The stack frame for which to retrieve the possible +// step-in targets." +// } +// }, +// "required": [ "frameId" ] +// }, +// "StepInTargetsResponse": { +// "allOf": [ { "$ref": "#/definitions/Response" }, { +// "type": "object", +// "description": "Response to `stepInTargets` request.", +// "properties": { +// "body": { +// "type": "object", +// "properties": { +// "targets": { +// "type": "array", +// "items": { +// "$ref": "#/definitions/StepInTarget" +// }, +// "description": "The possible step-in targets of the specified +// source location." +// } +// }, +// "required": [ "targets" ] +// } +// }, +// "required": [ "body" ] +// }] +// } +void request_stepInTargets(const llvm::json::Object ) { + llvm::json::Object response; + FillResponse(request, response); + auto arguments = request.getObject("arguments"); + + g_dap.step_in_targets.clear(); + lldb::SBFrame frame = g_dap.GetLLDBFrame(*arguments); + if (frame.IsValid()) { +lldb::SBAddress pc_addr = frame.GetPCAddress(); +lldb::addr_t line_end_addr = pc_addr.GetLineEntry() + .GetSameLineContiguousAddressRangeEnd( + /*include_inlined_functions=*/true) + .GetLoadAddress(g_dap.target); + +int max_inst_count = line_end_addr - pc_addr.GetLoadAddress(g_dap.target); +lldb::SBInstructionList insts = +g_dap.target.ReadInstructions(pc_addr, max_inst_count); + +if (!insts.IsValid()) { + response["success"] = false; + response["message"] = "Failed to get instructions for frame."; + g_dap.SendJSON(llvm::json::Value(std::move(response))); + return; +} + +llvm::json::Array step_in_targets; +const auto num_insts = insts.GetSize(); +for (size_t i = 0; i < num_insts; ++i) { + lldb::SBInstruction inst = insts.GetInstructionAtIndex(i); + if (!inst.IsValid()) +break; + + lldb::addr_t inst_addr = inst.GetAddress().GetLoadAddress(g_dap.target); + // line_end_addr is exclusive of the line range. + if (inst_addr >= line_end_addr) +break; + + // Note: currently only x86/x64 supports flow kind. + lldb::InstructionControlFlowKind flow_kind = + inst.GetControlFlowKind(g_dap.target); + if (flow_kind == lldb::eInstructionControlFlowKindCall) { +// Use call site instruction address as id which is easy to debug. +llvm::json::Object step_in_target; +step_in_target["id"] = inst_addr; + +llvm::StringRef call_operand_name = inst.GetOperands(g_dap.target); +lldb::addr_t call_target_addr; +if (call_operand_name.getAsInteger(0, call_target_addr)) + continue; + +lldb::SBAddress call_target_load_addr = +
[Lldb-commits] [lldb] Initial step in targets DAP support (PR #86623)
@@ -3180,14 +3180,159 @@ void request_stepIn(const llvm::json::Object ) { llvm::json::Object response; FillResponse(request, response); auto arguments = request.getObject("arguments"); + + std::string step_in_target; + uint64_t target_id = GetUnsigned(arguments, "targetId", 0); + auto it = g_dap.step_in_targets.find(target_id); + if (it != g_dap.step_in_targets.end()) +step_in_target = it->second; + + const bool single_thread = GetBoolean(arguments, "singleThread", false); + lldb::RunMode run_mode = + single_thread ? lldb::eOnlyThisThread : lldb::eOnlyDuringStepping; lldb::SBThread thread = g_dap.GetLLDBThread(*arguments); if (thread.IsValid()) { // Remember the thread ID that caused the resume so we can set the // "threadCausedFocus" boolean value in the "stopped" events. g_dap.focus_tid = thread.GetThreadID(); -thread.StepInto(); +thread.StepInto(step_in_target.c_str(), run_mode); + } else { +response["success"] = llvm::json::Value(false); + } + g_dap.SendJSON(llvm::json::Value(std::move(response))); +} + +// "StepInTargetsRequest": { +// "allOf": [ { "$ref": "#/definitions/Request" }, { +// "type": "object", +// "description": "This request retrieves the possible step-in targets for +// the specified stack frame.\nThese targets can be used in the `stepIn` +// request.\nClients should only call this request if the corresponding +// capability `supportsStepInTargetsRequest` is true.", "properties": { +// "command": { +// "type": "string", +// "enum": [ "stepInTargets" ] +// }, +// "arguments": { +// "$ref": "#/definitions/StepInTargetsArguments" +// } +// }, +// "required": [ "command", "arguments" ] +// }] +// }, +// "StepInTargetsArguments": { +// "type": "object", +// "description": "Arguments for `stepInTargets` request.", +// "properties": { +// "frameId": { +// "type": "integer", +// "description": "The stack frame for which to retrieve the possible +// step-in targets." +// } +// }, +// "required": [ "frameId" ] +// }, +// "StepInTargetsResponse": { +// "allOf": [ { "$ref": "#/definitions/Response" }, { +// "type": "object", +// "description": "Response to `stepInTargets` request.", +// "properties": { +// "body": { +// "type": "object", +// "properties": { +// "targets": { +// "type": "array", +// "items": { +// "$ref": "#/definitions/StepInTarget" +// }, +// "description": "The possible step-in targets of the specified +// source location." +// } +// }, +// "required": [ "targets" ] +// } +// }, +// "required": [ "body" ] +// }] +// } +void request_stepInTargets(const llvm::json::Object ) { + llvm::json::Object response; + FillResponse(request, response); + auto arguments = request.getObject("arguments"); + + g_dap.step_in_targets.clear(); + lldb::SBFrame frame = g_dap.GetLLDBFrame(*arguments); + if (frame.IsValid()) { +lldb::SBAddress pc_addr = frame.GetPCAddress(); +lldb::addr_t line_end_addr = pc_addr.GetLineEntry() + .GetSameLineContiguousAddressRangeEnd( + /*include_inlined_functions=*/true) + .GetLoadAddress(g_dap.target); + +int max_inst_count = line_end_addr - pc_addr.GetLoadAddress(g_dap.target); +lldb::SBInstructionList insts = +g_dap.target.ReadInstructions(pc_addr, max_inst_count); + +if (!insts.IsValid()) { + response["success"] = false; + response["message"] = "Failed to get instructions for frame."; + g_dap.SendJSON(llvm::json::Value(std::move(response))); + return; +} + +llvm::json::Array step_in_targets; +const auto num_insts = insts.GetSize(); +for (size_t i = 0; i < num_insts; ++i) { + lldb::SBInstruction inst = insts.GetInstructionAtIndex(i); + if (!inst.IsValid()) +break; + + lldb::addr_t inst_addr = inst.GetAddress().GetLoadAddress(g_dap.target); + // line_end_addr is exclusive of the line range. + if (inst_addr >= line_end_addr) +break; + + // Note: currently only x86/x64 supports flow kind. + lldb::InstructionControlFlowKind flow_kind = + inst.GetControlFlowKind(g_dap.target); + if (flow_kind == lldb::eInstructionControlFlowKindCall) { +// Use call site instruction address as id which is easy to debug. +llvm::json::Object step_in_target; +step_in_target["id"] = inst_addr; + +llvm::StringRef call_operand_name = inst.GetOperands(g_dap.target); +lldb::addr_t call_target_addr; +if (call_operand_name.getAsInteger(0, call_target_addr)) + continue; + +lldb::SBAddress call_target_load_addr = +
[Lldb-commits] [lldb] Initial step in targets DAP support (PR #86623)
@@ -3180,14 +3180,159 @@ void request_stepIn(const llvm::json::Object ) { llvm::json::Object response; FillResponse(request, response); auto arguments = request.getObject("arguments"); + + std::string step_in_target; + uint64_t target_id = GetUnsigned(arguments, "targetId", 0); + auto it = g_dap.step_in_targets.find(target_id); + if (it != g_dap.step_in_targets.end()) +step_in_target = it->second; + + const bool single_thread = GetBoolean(arguments, "singleThread", false); + lldb::RunMode run_mode = + single_thread ? lldb::eOnlyThisThread : lldb::eOnlyDuringStepping; lldb::SBThread thread = g_dap.GetLLDBThread(*arguments); if (thread.IsValid()) { // Remember the thread ID that caused the resume so we can set the // "threadCausedFocus" boolean value in the "stopped" events. g_dap.focus_tid = thread.GetThreadID(); -thread.StepInto(); +thread.StepInto(step_in_target.c_str(), run_mode); + } else { +response["success"] = llvm::json::Value(false); + } + g_dap.SendJSON(llvm::json::Value(std::move(response))); +} + +// "StepInTargetsRequest": { +// "allOf": [ { "$ref": "#/definitions/Request" }, { +// "type": "object", +// "description": "This request retrieves the possible step-in targets for +// the specified stack frame.\nThese targets can be used in the `stepIn` +// request.\nClients should only call this request if the corresponding +// capability `supportsStepInTargetsRequest` is true.", "properties": { +// "command": { +// "type": "string", +// "enum": [ "stepInTargets" ] +// }, +// "arguments": { +// "$ref": "#/definitions/StepInTargetsArguments" +// } +// }, +// "required": [ "command", "arguments" ] +// }] +// }, +// "StepInTargetsArguments": { +// "type": "object", +// "description": "Arguments for `stepInTargets` request.", +// "properties": { +// "frameId": { +// "type": "integer", +// "description": "The stack frame for which to retrieve the possible +// step-in targets." +// } +// }, +// "required": [ "frameId" ] +// }, +// "StepInTargetsResponse": { +// "allOf": [ { "$ref": "#/definitions/Response" }, { +// "type": "object", +// "description": "Response to `stepInTargets` request.", +// "properties": { +// "body": { +// "type": "object", +// "properties": { +// "targets": { +// "type": "array", +// "items": { +// "$ref": "#/definitions/StepInTarget" +// }, +// "description": "The possible step-in targets of the specified +// source location." +// } +// }, +// "required": [ "targets" ] +// } +// }, +// "required": [ "body" ] +// }] +// } +void request_stepInTargets(const llvm::json::Object ) { + llvm::json::Object response; + FillResponse(request, response); + auto arguments = request.getObject("arguments"); + + g_dap.step_in_targets.clear(); + lldb::SBFrame frame = g_dap.GetLLDBFrame(*arguments); + if (frame.IsValid()) { +lldb::SBAddress pc_addr = frame.GetPCAddress(); +lldb::addr_t line_end_addr = pc_addr.GetLineEntry() + .GetSameLineContiguousAddressRangeEnd( + /*include_inlined_functions=*/true) + .GetLoadAddress(g_dap.target); + +int max_inst_count = line_end_addr - pc_addr.GetLoadAddress(g_dap.target); +lldb::SBInstructionList insts = +g_dap.target.ReadInstructions(pc_addr, max_inst_count); walter-erquinigo wrote: Please write a new `ReadInstructions` API that is range based. Internally you can use `Disassembler::DisassembleRange`. That way you'll decode only the minimum necessary instructions. https://github.com/llvm/llvm-project/pull/86623 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Initial step in targets DAP support (PR #86623)
@@ -0,0 +1,66 @@ +""" +Test lldb-dap stepInTargets request +""" + +import dap_server +from lldbsuite.test.decorators import * +from lldbsuite.test.lldbtest import * +import lldbdap_testcase +from lldbsuite.test import lldbutil + + +class TestDAP_stepInTargets(lldbdap_testcase.DAPTestCaseBase): +@skipIf(archs=no_match(["x86_64"])) # ARM flow kind is not supported yet. walter-erquinigo wrote: mention that this doesn't work on arm because of lack of InstructionControlFlowKind support https://github.com/llvm/llvm-project/pull/86623 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Change GetNumChildren()/CalculateNumChildren() methods return llvm::Expected (PR #84219)
@@ -1397,7 +1398,9 @@ ValueObjectSP GetValueForOffset(StackFrame , ValueObjectSP , return parent; } - for (int ci = 0, ce = parent->GetNumChildren(); ci != ce; ++ci) { + for (int ci = 0, ce = llvm::expectedToStdOptional(parent->GetNumChildren()) walter-erquinigo wrote: I'm afraid that calls to `expectedToStdOptional` will just silence important warnings. https://github.com/llvm/llvm-project/pull/84219 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Change GetNumChildren()/CalculateNumChildren() methods return llvm::Expected (PR #84219)
@@ -451,8 +451,13 @@ bool FormatManager::ShouldPrintAsOneLiner(ValueObject ) { if (valobj.GetSummaryFormat().get() != nullptr) return valobj.GetSummaryFormat()->IsOneLiner(); + auto num_children = valobj.GetNumChildren(); + if (!num_children) { +llvm::consumeError(num_children.takeError()); walter-erquinigo wrote: could you log this some channel instead of consuming the error? That would still be NFC and would fit well within this PR https://github.com/llvm/llvm-project/pull/84219 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Increase timeout to reduce test failure rate. (PR #83312)
@@ -6,6 +6,7 @@ class DAPTestCaseBase(TestBase): +timeoutval = 10 * (10 if ('ASAN_OPTIONS' in os.environ) else 1) walter-erquinigo wrote: Please add a comment here mentioning what the purpose of this variable is https://github.com/llvm/llvm-project/pull/83312 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Increase timeout to reduce test failure rate. (PR #83312)
https://github.com/walter-erquinigo edited https://github.com/llvm/llvm-project/pull/83312 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Increase timeout to reduce test failure rate. (PR #83312)
https://github.com/walter-erquinigo approved this pull request. Other than a missing comment, this LGTM. Thanks! https://github.com/llvm/llvm-project/pull/83312 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Increase timeout to reduce test failure rate. (PR #83312)
https://github.com/walter-erquinigo edited https://github.com/llvm/llvm-project/pull/83312 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] Increase timeout to reduce test failure rate. (PR #83312)
https://github.com/walter-erquinigo requested changes to this pull request. could you create instead a variable at the base test class level that can be used by other DAP tests when setting timeouts? I'm pretty sure at least one other test file uses timeouts. https://github.com/llvm/llvm-project/pull/83312 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Fix completion of space-only lines in the REPL on Linux (PR #83203)
https://github.com/walter-erquinigo closed https://github.com/llvm/llvm-project/pull/83203 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Fix completion of space-only lines in the REPL on Linux (PR #83203)
@@ -54,3 +55,16 @@ def test_basic_completion(self): self.expect_repl("$persistent + 10", substrs=["(long) $2 = 17"]) self.quit() + +# PExpect uses many timeouts internally and doesn't play well +# under ASAN on a loaded machine.. +@skipIfAsan +@skipIf(oslist=["linux"], archs=["arm", "aarch64"]) # Randomly fails on buildbot walter-erquinigo wrote: I actually don't know. The existing test already has issues with basic expr eval, and the new test will have them as well, so I decided to just copy the same configuration. https://github.com/llvm/llvm-project/pull/83203 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Fix completion of space-only lines in the REPL on Linux (PR #83203)
walter-erquinigo wrote: @DavidSpickett I was able to write a test for this. PTAL :) https://github.com/llvm/llvm-project/pull/83203 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Fix completion of space-only lines in the REPL on Linux (PR #83203)
https://github.com/walter-erquinigo updated https://github.com/llvm/llvm-project/pull/83203 >From 3410fc7e0e9d73763e3edee6e008012ba571ad80 Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Tue, 27 Feb 2024 17:59:20 -0500 Subject: [PATCH] [LLDB] Fix completion of space-only lines in the REPL on Linux https://github.com/modularml/mojo/issues/1796 discovered that if you try to complete a space-only line in the REPL on Linux, LLDB crashes. I suspect that editline doesn't behave the same way on linux and on darwin, because I can't replicate this on darwin. Adding a boundary check in the completion code prevents the crash from happening. --- lldb/source/Host/common/Editline.cpp | 5 +++- lldb/test/API/repl/clang/TestClangREPL.py | 32 --- 2 files changed, 27 insertions(+), 10 deletions(-) diff --git a/lldb/source/Host/common/Editline.cpp b/lldb/source/Host/common/Editline.cpp index ce707e530d008b..e66271e8a6ee99 100644 --- a/lldb/source/Host/common/Editline.cpp +++ b/lldb/source/Host/common/Editline.cpp @@ -1029,8 +1029,11 @@ unsigned char Editline::TabCommand(int ch) { case CompletionMode::Normal: { std::string to_add = completion.GetCompletion(); // Terminate the current argument with a quote if it started with a quote. - if (!request.GetParsedLine().empty() && request.GetParsedArg().IsQuoted()) + Args = request.GetParsedLine(); + if (!parsedLine.empty() && request.GetCursorIndex() < parsedLine.size() && + request.GetParsedArg().IsQuoted()) { to_add.push_back(request.GetParsedArg().GetQuoteChar()); + } to_add.push_back(' '); el_deletestr(m_editline, request.GetCursorArgumentPrefix().size()); el_insertstr(m_editline, to_add.c_str()); diff --git a/lldb/test/API/repl/clang/TestClangREPL.py b/lldb/test/API/repl/clang/TestClangREPL.py index 0b67955a7833c6..c37557fb94735d 100644 --- a/lldb/test/API/repl/clang/TestClangREPL.py +++ b/lldb/test/API/repl/clang/TestClangREPL.py @@ -1,7 +1,6 @@ -import lldb from lldbsuite.test.decorators import * -from lldbsuite.test.lldbtest import * from lldbsuite.test.lldbpexpect import PExpectTest +from lldbsuite.test.lldbtest import * class TestCase(PExpectTest): @@ -17,13 +16,7 @@ def expect_repl(self, expr, substrs=[]): self.current_repl_line_number += 1 self.child.expect_exact(str(self.current_repl_line_number) + ">") -# PExpect uses many timeouts internally and doesn't play well -# under ASAN on a loaded machine.. -@skipIfAsan -@skipIf(oslist=["linux"], archs=["arm", "aarch64"]) # Randomly fails on buildbot -@skipIfEditlineSupportMissing -def test_basic_completion(self): -"""Test that we can complete a simple multiline expression""" +def start_repl(self): self.build() self.current_repl_line_number = 1 @@ -41,6 +34,14 @@ def test_basic_completion(self): self.child.send("expression --repl -l c --\n") self.child.expect_exact("1>") +# PExpect uses many timeouts internally and doesn't play well +# under ASAN on a loaded machine.. +@skipIfAsan +@skipIf(oslist=["linux"], archs=["arm", "aarch64"]) # Randomly fails on buildbot +@skipIfEditlineSupportMissing +def test_basic_completion(self): +"""Test that we can complete a simple multiline expression""" +self.start_repl() # Try evaluating a simple expression. self.expect_repl("3 + 3", substrs=["(int) $0 = 6"]) @@ -54,3 +55,16 @@ def test_basic_completion(self): self.expect_repl("$persistent + 10", substrs=["(long) $2 = 17"]) self.quit() + +# PExpect uses many timeouts internally and doesn't play well +# under ASAN on a loaded machine.. +@skipIfAsan +@skipIf(oslist=["linux"], archs=["arm", "aarch64"]) # Randomly fails on buildbot +@skipIfEditlineSupportMissing +def test_completion_with_space_only_line(self): +"""Test that we don't crash when completing lines with spaces only""" +self.start_repl() + +self.child.send(" ") +self.child.send("\t") +self.expect_repl("3 + 3", substrs=["(int) $0 = 6"]) ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [LLDB] Fix completion of space-only lines in the REPL on Linux (PR #83203)
https://github.com/walter-erquinigo created https://github.com/llvm/llvm-project/pull/83203 https://github.com/modularml/mojo/issues/1796 discovered that if you try to complete a space-only line in the REPL on Linux, LLDB crashes. I suspect that editline doesn't behave the same way on linux and on darwin, because I can't replicate this on darwin. Adding a boundary check in the completion code prevents the crash from happening. >From 8dcc86a33bf10547f4a1c4175830b50a0508efe0 Mon Sep 17 00:00:00 2001 From: walter erquinigo Date: Tue, 27 Feb 2024 17:59:20 -0500 Subject: [PATCH] [LLDB] Fix completion of space-only lines in the REPL on Linux https://github.com/modularml/mojo/issues/1796 discovered that if you try to complete a space-only line in the REPL on Linux, LLDB crashes. I suspect that editline doesn't behave the same way on linux and on darwin, because I can't replicate this on darwin. Adding a boundary check in the completion code prevents the crash from happening. --- lldb/source/Host/common/Editline.cpp | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/lldb/source/Host/common/Editline.cpp b/lldb/source/Host/common/Editline.cpp index ce707e530d008b..e66271e8a6ee99 100644 --- a/lldb/source/Host/common/Editline.cpp +++ b/lldb/source/Host/common/Editline.cpp @@ -1029,8 +1029,11 @@ unsigned char Editline::TabCommand(int ch) { case CompletionMode::Normal: { std::string to_add = completion.GetCompletion(); // Terminate the current argument with a quote if it started with a quote. - if (!request.GetParsedLine().empty() && request.GetParsedArg().IsQuoted()) + Args = request.GetParsedLine(); + if (!parsedLine.empty() && request.GetCursorIndex() < parsedLine.size() && + request.GetParsedArg().IsQuoted()) { to_add.push_back(request.GetParsedArg().GetQuoteChar()); + } to_add.push_back(' '); el_deletestr(m_editline, request.GetCursorArgumentPrefix().size()); el_insertstr(m_editline, to_add.c_str()); ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [lldb][dap] Avoid concurrent `HandleCommand` calls (PR #83162)
https://github.com/walter-erquinigo approved this pull request. This is amazing! That finally explains some flakes I've seen https://github.com/llvm/llvm-project/pull/83162 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [lldb-dap] Add support for data breakpoint. (PR #81541)
walter-erquinigo wrote: I think using @ is fine, but we can revisit it later if we see any issues. https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [lldb-dap] Add support for data breakpoint. (PR #81541)
https://github.com/walter-erquinigo approved this pull request. https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [lldb-dap] Add support for data breakpoint. (PR #81541)
@@ -2591,6 +2594,248 @@ void request_setFunctionBreakpoints(const llvm::json::Object ) { g_dap.SendJSON(llvm::json::Value(std::move(response))); } +// "DataBreakpointInfoRequest": { +// "allOf": [ { "$ref": "#/definitions/Request" }, { +// "type": "object", +// "description": "Obtains information on a possible data breakpoint that +// could be set on an expression or variable.\nClients should only call this +// request if the corresponding capability `supportsDataBreakpoints` is +// true.", "properties": { +// "command": { +// "type": "string", +// "enum": [ "dataBreakpointInfo" ] +// }, +// "arguments": { +// "$ref": "#/definitions/DataBreakpointInfoArguments" +// } +// }, +// "required": [ "command", "arguments" ] +// }] +// }, +// "DataBreakpointInfoArguments": { +// "type": "object", +// "description": "Arguments for `dataBreakpointInfo` request.", +// "properties": { +// "variablesReference": { +// "type": "integer", +// "description": "Reference to the variable container if the data +// breakpoint is requested for a child of the container. The +// `variablesReference` must have been obtained in the current suspended +// state. See 'Lifetime of Object References' in the Overview section for +// details." +// }, +// "name": { +// "type": "string", +// "description": "The name of the variable's child to obtain data +// breakpoint information for.\nIf `variablesReference` isn't specified, +// this can be an expression." +// }, +// "frameId": { +// "type": "integer", +// "description": "When `name` is an expression, evaluate it in the scope +// of this stack frame. If not specified, the expression is evaluated in +// the global scope. When `variablesReference` is specified, this property +// has no effect." +// } +// }, +// "required": [ "name" ] +// }, +// "DataBreakpointInfoResponse": { +// "allOf": [ { "$ref": "#/definitions/Response" }, { +// "type": "object", +// "description": "Response to `dataBreakpointInfo` request.", +// "properties": { +// "body": { +// "type": "object", +// "properties": { +// "dataId": { +// "type": [ "string", "null" ], +// "description": "An identifier for the data on which a data +// breakpoint can be registered with the `setDataBreakpoints` +// request or null if no data breakpoint is available. If a +// `variablesReference` or `frameId` is passed, the `dataId` is +// valid in the current suspended state, otherwise it's valid +// indefinitely. See 'Lifetime of Object References' in the Overview +// section for details. Breakpoints set using the `dataId` in the +// `setDataBreakpoints` request may outlive the lifetime of the +// associated `dataId`." +// }, +// "description": { +// "type": "string", +// "description": "UI string that describes on what data the +// breakpoint is set on or why a data breakpoint is not available." +// }, +// "accessTypes": { +// "type": "array", +// "items": { +// "$ref": "#/definitions/DataBreakpointAccessType" +// }, +// "description": "Attribute lists the available access types for a +// potential data breakpoint. A UI client could surface this +// information." +// }, +// "canPersist": { +// "type": "boolean", +// "description": "Attribute indicates that a potential data +// breakpoint could be persisted across sessions." +// } +// }, +// "required": [ "dataId", "description" ] +// } +// }, +// "required": [ "body" ] +// }] +// } +void request_dataBreakpointInfo(const llvm::json::Object ) { + llvm::json::Object response; + FillResponse(request, response); + llvm::json::Object body; + lldb::SBError error; + llvm::json::Array accessTypes{"read", "write", "readWrite"}; + const auto *arguments = request.getObject("arguments"); + const auto variablesReference = + GetUnsigned(arguments, "variablesReference", 0); walter-erquinigo wrote: it'd be better to use a non-zero default value, which might collide with an actual variable ref id https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [lldb-dap] Add support for data breakpoint. (PR #81541)
@@ -2591,6 +2594,248 @@ void request_setFunctionBreakpoints(const llvm::json::Object ) { g_dap.SendJSON(llvm::json::Value(std::move(response))); } +// "DataBreakpointInfoRequest": { +// "allOf": [ { "$ref": "#/definitions/Request" }, { +// "type": "object", +// "description": "Obtains information on a possible data breakpoint that +// could be set on an expression or variable.\nClients should only call this +// request if the corresponding capability `supportsDataBreakpoints` is +// true.", "properties": { +// "command": { +// "type": "string", +// "enum": [ "dataBreakpointInfo" ] +// }, +// "arguments": { +// "$ref": "#/definitions/DataBreakpointInfoArguments" +// } +// }, +// "required": [ "command", "arguments" ] +// }] +// }, +// "DataBreakpointInfoArguments": { +// "type": "object", +// "description": "Arguments for `dataBreakpointInfo` request.", +// "properties": { +// "variablesReference": { +// "type": "integer", +// "description": "Reference to the variable container if the data +// breakpoint is requested for a child of the container. The +// `variablesReference` must have been obtained in the current suspended +// state. See 'Lifetime of Object References' in the Overview section for +// details." +// }, +// "name": { +// "type": "string", +// "description": "The name of the variable's child to obtain data +// breakpoint information for.\nIf `variablesReference` isn't specified, +// this can be an expression." +// }, +// "frameId": { +// "type": "integer", +// "description": "When `name` is an expression, evaluate it in the scope +// of this stack frame. If not specified, the expression is evaluated in +// the global scope. When `variablesReference` is specified, this property +// has no effect." +// } +// }, +// "required": [ "name" ] +// }, +// "DataBreakpointInfoResponse": { +// "allOf": [ { "$ref": "#/definitions/Response" }, { +// "type": "object", +// "description": "Response to `dataBreakpointInfo` request.", +// "properties": { +// "body": { +// "type": "object", +// "properties": { +// "dataId": { +// "type": [ "string", "null" ], +// "description": "An identifier for the data on which a data +// breakpoint can be registered with the `setDataBreakpoints` +// request or null if no data breakpoint is available. If a +// `variablesReference` or `frameId` is passed, the `dataId` is +// valid in the current suspended state, otherwise it's valid +// indefinitely. See 'Lifetime of Object References' in the Overview +// section for details. Breakpoints set using the `dataId` in the +// `setDataBreakpoints` request may outlive the lifetime of the +// associated `dataId`." +// }, +// "description": { +// "type": "string", +// "description": "UI string that describes on what data the +// breakpoint is set on or why a data breakpoint is not available." +// }, +// "accessTypes": { +// "type": "array", +// "items": { +// "$ref": "#/definitions/DataBreakpointAccessType" +// }, +// "description": "Attribute lists the available access types for a +// potential data breakpoint. A UI client could surface this +// information." +// }, +// "canPersist": { +// "type": "boolean", +// "description": "Attribute indicates that a potential data +// breakpoint could be persisted across sessions." +// } +// }, +// "required": [ "dataId", "description" ] +// } +// }, +// "required": [ "body" ] +// }] +// } +void request_dataBreakpointInfo(const llvm::json::Object ) { + llvm::json::Object response; + FillResponse(request, response); + llvm::json::Object body; + lldb::SBError error; + llvm::json::Array accessTypes{"read", "write", "readWrite"}; + const auto *arguments = request.getObject("arguments"); + const auto variablesReference = + GetUnsigned(arguments, "variablesReference", 0); + llvm::StringRef name = GetString(arguments, "name"); + lldb::SBFrame frame = g_dap.GetLLDBFrame(*arguments); + bool is_duplicated_variable_name = name.contains(" @"); + + lldb::SBValue variable; + if (lldb::SBValueList *top_scope = GetTopLevelScope(variablesReference)) { +// variablesReference is one of our scopes, not an actual variable it is +// asking for a variable in locals or globals or registers +int64_t end_idx = top_scope->GetSize(); +// Searching backward so that we choose the variable in closest scope +// among variables of the same name. +
[Lldb-commits] [lldb] [llvm] [lldb-dap] Add support for data breakpoint. (PR #81541)
https://github.com/walter-erquinigo commented: Amazing stuff! I've been wanting this for a while. I left some minor comments. https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [lldb-dap] Add support for data breakpoint. (PR #81541)
https://github.com/walter-erquinigo edited https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [WIP][lldb-dap] Add support for data breakpoint. (PR #81541)
walter-erquinigo wrote: just ping me when this PR is rebased https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [lldb-dap][NFC] Add Breakpoint struct to share common logic. (PR #80753)
https://github.com/walter-erquinigo approved this pull request. thanks! https://github.com/llvm/llvm-project/pull/80753 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [WIP][lldb-dap] Add support for data breakpoint. (PR #81541)
@@ -895,6 +906,32 @@ def request_setFunctionBreakpoints(self, names, condition=None, hitCondition=Non } return self.send_recv(command_dict) +def request_dataBreakpointInfo(self, variablesReference, name): +args_dict = {"variablesReference": variablesReference, "name": name} +command_dict = { +"command": "dataBreakpointInfo", +"type": "request", +"arguments": args_dict, +} +return self.send_recv(command_dict) + +def request_setDataBreakpoint(self, dataBreakpoints): +"""dataBreakpoints is a list of dictionary with following fields: walter-erquinigo wrote: `list of dictionary` sounds very weird. Did you mean something else? https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits
[Lldb-commits] [lldb] [llvm] [WIP][lldb-dap] Add support for data breakpoint. (PR #81541)
https://github.com/walter-erquinigo commented: This looks great overall! Could you split this PR into two? One with the refactoring and another one with the new features? That would make reviewing easier https://github.com/llvm/llvm-project/pull/81541 ___ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits