https://github.com/chelcassanova updated https://github.com/llvm/llvm-project/pull/91404
>From c4ee8ba1f6eff974614c9a98e660d22a1691bdb4 Mon Sep 17 00:00:00 2001 From: Chelsea Cassanova <chelsea_cassan...@apple.com> Date: Thu, 9 May 2024 11:08:29 -0700 Subject: [PATCH] [lldb][breakpoint] Grey out disabled breakpoints This commit adds colour settings to the list of breakpoints in order to grey out breakpoints that have been disabled. --- lldb/include/lldb/API/SBStream.h | 5 +++ lldb/include/lldb/Core/Debugger.h | 4 +++ lldb/include/lldb/Utility/Stream.h | 8 +++++ lldb/source/API/SBStream.cpp | 10 ++++++ lldb/source/Breakpoint/Breakpoint.cpp | 11 +++++++ lldb/source/Core/CoreProperties.td | 10 ++++++ lldb/source/Core/Debugger.cpp | 12 +++++++ lldb/source/Utility/Stream.cpp | 8 +++++ .../API/terminal/TestDisabledBreakpoints.py | 32 +++++++++++++++++++ 9 files changed, 100 insertions(+) create mode 100644 lldb/test/API/terminal/TestDisabledBreakpoints.py diff --git a/lldb/include/lldb/API/SBStream.h b/lldb/include/lldb/API/SBStream.h index d230da6123fb36..66a56322a9f958 100644 --- a/lldb/include/lldb/API/SBStream.h +++ b/lldb/include/lldb/API/SBStream.h @@ -12,6 +12,7 @@ #include <cstdio> #include "lldb/API/SBDefines.h" +#include "llvm/ADT/StringRef.h" namespace lldb_private { class ScriptInterpreter; @@ -47,6 +48,10 @@ class LLDB_API SBStream { void Print(const char *str); + bool HasColor(); + + void FormatAnsiTerminalCodes(llvm::StringRef format); + void RedirectToFile(const char *path, bool append); void RedirectToFile(lldb::SBFile file); diff --git a/lldb/include/lldb/Core/Debugger.h b/lldb/include/lldb/Core/Debugger.h index 1d5f2fcc20626c..4f04335b42bbc7 100644 --- a/lldb/include/lldb/Core/Debugger.h +++ b/lldb/include/lldb/Core/Debugger.h @@ -308,6 +308,10 @@ class Debugger : public std::enable_shared_from_this<Debugger>, llvm::StringRef GetShowProgressAnsiSuffix() const; + llvm::StringRef GetDisabledBreakpointAnsiPrefix() const; + + llvm::StringRef GetDisabledBreakpointAnsiSuffix() const; + bool GetUseAutosuggestion() const; llvm::StringRef GetAutosuggestionAnsiPrefix() const; diff --git a/lldb/include/lldb/Utility/Stream.h b/lldb/include/lldb/Utility/Stream.h index 37bcdc99241715..1ab590202cd694 100644 --- a/lldb/include/lldb/Utility/Stream.h +++ b/lldb/include/lldb/Utility/Stream.h @@ -309,6 +309,12 @@ class Stream { /// The current indentation level. unsigned GetIndentLevel() const; + /// Whether or not the stream is using color. + /// + /// \return + /// The color setting of the stream. + bool HasColor(); + /// Indent the current line in the stream. /// /// Indent the current line using the current indentation level and print an @@ -366,6 +372,8 @@ class Stream { /// The optional C string format that can be overridden. void QuotedCString(const char *cstr, const char *format = "\"%s\""); + void FormatAnsiTerminalCodes(llvm::StringRef format); + /// Set the address size in bytes. /// /// \param[in] addr_size diff --git a/lldb/source/API/SBStream.cpp b/lldb/source/API/SBStream.cpp index fc8f09a7bb9ae5..bc0f3356d4753c 100644 --- a/lldb/source/API/SBStream.cpp +++ b/lldb/source/API/SBStream.cpp @@ -11,6 +11,7 @@ #include "lldb/API/SBFile.h" #include "lldb/Host/FileSystem.h" #include "lldb/Host/StreamFile.h" +#include "lldb/Utility/AnsiTerminal.h" #include "lldb/Utility/Instrumentation.h" #include "lldb/Utility/LLDBLog.h" #include "lldb/Utility/Status.h" @@ -77,6 +78,15 @@ void SBStream::Printf(const char *format, ...) { va_end(args); } +bool SBStream::HasColor() { + return m_opaque_up->AsRawOstream().colors_enabled(); +} + +void SBStream::FormatAnsiTerminalCodes(llvm::StringRef format) { + if (HasColor()) + Printf("%s", ansi::FormatAnsiTerminalCodes(format).c_str()); +} + void SBStream::RedirectToFile(const char *path, bool append) { LLDB_INSTRUMENT_VA(this, path, append); diff --git a/lldb/source/Breakpoint/Breakpoint.cpp b/lldb/source/Breakpoint/Breakpoint.cpp index 54ebafc3f65b5c..550671bfbee9d9 100644 --- a/lldb/source/Breakpoint/Breakpoint.cpp +++ b/lldb/source/Breakpoint/Breakpoint.cpp @@ -15,6 +15,7 @@ #include "lldb/Breakpoint/BreakpointResolver.h" #include "lldb/Breakpoint/BreakpointResolverFileLine.h" #include "lldb/Core/Address.h" +#include "lldb/Core/Debugger.h" #include "lldb/Core/Module.h" #include "lldb/Core/ModuleList.h" #include "lldb/Core/SearchFilter.h" @@ -26,6 +27,7 @@ #include "lldb/Target/SectionLoadList.h" #include "lldb/Target/Target.h" #include "lldb/Target/ThreadSpec.h" +#include "lldb/Utility/AnsiTerminal.h" #include "lldb/Utility/LLDBLog.h" #include "lldb/Utility/Log.h" #include "lldb/Utility/Stream.h" @@ -838,6 +840,11 @@ void Breakpoint::GetDescription(Stream *s, lldb::DescriptionLevel level, bool show_locations) { assert(s != nullptr); + // Grey out any disabled breakpoints in the list of breakpoints. + if (!IsEnabled()) + s->FormatAnsiTerminalCodes( + GetTarget().GetDebugger().GetDisabledBreakpointAnsiPrefix()); + if (!m_kind_description.empty()) { if (level == eDescriptionLevelBrief) { s->PutCString(GetBreakpointKind()); @@ -934,6 +941,10 @@ void Breakpoint::GetDescription(Stream *s, lldb::DescriptionLevel level, } s->IndentLess(); } + + // Reset the colors back to normal if they were previously greyed out. + s->FormatAnsiTerminalCodes( + GetTarget().GetDebugger().GetDisabledBreakpointAnsiSuffix()); } void Breakpoint::GetResolverDescription(Stream *s) { diff --git a/lldb/source/Core/CoreProperties.td b/lldb/source/Core/CoreProperties.td index e11aad2660b461..9fcbcd78b34215 100644 --- a/lldb/source/Core/CoreProperties.td +++ b/lldb/source/Core/CoreProperties.td @@ -168,6 +168,16 @@ let Definition = "debugger" in { Global, DefaultStringValue<"${ansi.normal}">, Desc<"When displaying progress in a color-enabled terminal, use the ANSI terminal code specified in this format immediately after the progress message.">; + + def ShowDisabledBreakpointAnsiPrefix: Property<"disable-breakpoint-ansi-prefix", "String">, + Global, + DefaultStringValue<"${ansi.faint}">, + Desc<"When a disabled breakpoint is viewed in a color-enabled terminal, use the ANSI terminal code specified immediately before any disabled breakpoints.">; + def ShowDisabledBreakpointAnsiSuffix: Property<"disable-breakpoint-ansi-suffix", "String">, + Global, + DefaultStringValue<"${ansi.normal}">, + Desc<"When a disabled breakpoint is viewed in a color-enabled terminal, use the ANSI terminal code specified immediately after any disabled breakpoints.">; + def UseSourceCache: Property<"use-source-cache", "Boolean">, Global, DefaultTrue, diff --git a/lldb/source/Core/Debugger.cpp b/lldb/source/Core/Debugger.cpp index c666a753343c9d..3491d959851788 100644 --- a/lldb/source/Core/Debugger.cpp +++ b/lldb/source/Core/Debugger.cpp @@ -436,6 +436,18 @@ llvm::StringRef Debugger::GetShowProgressAnsiSuffix() const { idx, g_debugger_properties[idx].default_cstr_value); } +llvm::StringRef Debugger::GetDisabledBreakpointAnsiPrefix() const { + const uint32_t idx = ePropertyShowDisabledBreakpointAnsiPrefix; + return GetPropertyAtIndexAs<llvm::StringRef>( + idx, g_debugger_properties[idx].default_cstr_value); +} + +llvm::StringRef Debugger::GetDisabledBreakpointAnsiSuffix() const { + const uint32_t idx = ePropertyShowDisabledBreakpointAnsiSuffix; + return GetPropertyAtIndexAs<llvm::StringRef>( + idx, g_debugger_properties[idx].default_cstr_value); +} + bool Debugger::GetUseAutosuggestion() const { const uint32_t idx = ePropertyShowAutosuggestion; return GetPropertyAtIndexAs<bool>( diff --git a/lldb/source/Utility/Stream.cpp b/lldb/source/Utility/Stream.cpp index 89dce9fb0e1f71..e4ca9ad5a1f14d 100644 --- a/lldb/source/Utility/Stream.cpp +++ b/lldb/source/Utility/Stream.cpp @@ -103,6 +103,11 @@ void Stream::QuotedCString(const char *cstr, const char *format) { Printf(format, cstr); } +void Stream::FormatAnsiTerminalCodes(llvm::StringRef format) { + if (HasColor()) + Printf("%s", ansi::FormatAnsiTerminalCodes(format).c_str()); +} + // Put an address "addr" out to the stream with optional prefix and suffix // strings. void lldb_private::DumpAddress(llvm::raw_ostream &s, uint64_t addr, @@ -186,6 +191,9 @@ Stream &Stream::operator<<(const void *p) { // Get the current indentation level unsigned Stream::GetIndentLevel() const { return m_indent_level; } +// Get the color setting of the stream. +bool Stream::HasColor() { return m_forwarder.colors_enabled(); } + // Set the current indentation level void Stream::SetIndentLevel(unsigned indent_level) { m_indent_level = indent_level; diff --git a/lldb/test/API/terminal/TestDisabledBreakpoints.py b/lldb/test/API/terminal/TestDisabledBreakpoints.py new file mode 100644 index 00000000000000..052551baf51600 --- /dev/null +++ b/lldb/test/API/terminal/TestDisabledBreakpoints.py @@ -0,0 +1,32 @@ +""" +Test that disabling breakpoints and viewing them in a list uses the correct ANSI color settings when colors are enabled and disabled. +""" +import lldb +from lldbsuite.test.decorators import * +from lldbsuite.test.lldbtest import * +from lldbsuite.test import lldbutil +from lldbsuite.test.lldbpexpect import PExpectTest + +import re +import io + + +class DisabledBreakpointsTest(PExpectTest): + @add_test_categories(["pexpect"]) + def test_disabling_breakpoints_with_color(self): + """Test that disabling a breakpoint and viewing the breakpoints list uses the specified ANSI color prefix.""" + import pexpect + + self.child = pexpect.spawn("expect", encoding="utf-8") + + ansi_red_color_code = "\x1b[31m" + + self.launch(use_colors=True, dimensions=(100, 100)) + self.child.sendline( + 'settings set disable-breakpoint-ansi-prefix "${ansi.fg.red}"' + ) + self.child.sendline("b main") + self.child.sendline("br dis") + self.child.sendline("br l") + self.child.expect_exact(ansi_red_color_code + "1:") + self.quit() _______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits