Skip to content

[lldb] Log swift-healthcheck messages to the system console #8691

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 1 addition & 2 deletions lldb/include/lldb/Core/Debugger.h
Original file line number Diff line number Diff line change
Expand Up @@ -639,8 +639,7 @@ class Debugger : public std::enable_shared_from_this<Debugger>,
std::optional<lldb::user_id_t> debugger_id,
uint32_t progress_category_bit = eBroadcastBitProgress);

static void ReportDiagnosticImpl(DiagnosticEventData::Type type,
std::string message,
static void ReportDiagnosticImpl(lldb::Severity severity, std::string message,
std::optional<lldb::user_id_t> debugger_id,
std::once_flag *once);

Expand Down
14 changes: 5 additions & 9 deletions lldb/include/lldb/Core/DebuggerEvents.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,19 +76,15 @@ class ProgressEventData : public EventData {

class DiagnosticEventData : public EventData {
public:
enum class Type {
Info,
Warning,
Error,
};
DiagnosticEventData(Type type, std::string message, bool debugger_specific)
: m_message(std::move(message)), m_type(type),
DiagnosticEventData(lldb::Severity severity, std::string message,
bool debugger_specific)
: m_message(std::move(message)), m_severity(severity),
m_debugger_specific(debugger_specific) {}
~DiagnosticEventData() override = default;

const std::string &GetMessage() const { return m_message; }
bool IsDebuggerSpecific() const { return m_debugger_specific; }
Type GetType() const { return m_type; }
lldb::Severity GetSeverity() const { return m_severity; }

llvm::StringRef GetPrefix() const;

Expand All @@ -105,7 +101,7 @@ class DiagnosticEventData : public EventData {

protected:
std::string m_message;
Type m_type;
lldb::Severity m_severity;
const bool m_debugger_specific;

DiagnosticEventData(const DiagnosticEventData &) = delete;
Expand Down
18 changes: 6 additions & 12 deletions lldb/include/lldb/Expression/DiagnosticManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,12 +28,6 @@ enum DiagnosticOrigin {
eDiagnosticOriginLLVM
};

enum DiagnosticSeverity {
eDiagnosticSeverityError,
eDiagnosticSeverityWarning,
eDiagnosticSeverityRemark
};

const uint32_t LLDB_INVALID_COMPILER_ID = UINT32_MAX;

class Diagnostic {
Expand All @@ -55,7 +49,7 @@ class Diagnostic {
}
}

Diagnostic(llvm::StringRef message, DiagnosticSeverity severity,
Diagnostic(llvm::StringRef message, lldb::Severity severity,
DiagnosticOrigin origin, uint32_t compiler_id)
: m_message(message), m_severity(severity), m_origin(origin),
m_compiler_id(compiler_id) {}
Expand All @@ -68,7 +62,7 @@ class Diagnostic {

virtual bool HasFixIts() const { return false; }

DiagnosticSeverity GetSeverity() const { return m_severity; }
lldb::Severity GetSeverity() const { return m_severity; }

uint32_t GetCompilerID() const { return m_compiler_id; }

Expand All @@ -83,7 +77,7 @@ class Diagnostic {

protected:
std::string m_message;
DiagnosticSeverity m_severity;
lldb::Severity m_severity;
DiagnosticOrigin m_origin;
uint32_t m_compiler_id; // Compiler-specific diagnostic ID
};
Expand All @@ -106,7 +100,7 @@ class DiagnosticManager {
});
}

void AddDiagnostic(llvm::StringRef message, DiagnosticSeverity severity,
void AddDiagnostic(llvm::StringRef message, lldb::Severity severity,
DiagnosticOrigin origin,
uint32_t compiler_id = LLDB_INVALID_COMPILER_ID) {
m_diagnostics.emplace_back(
Expand All @@ -127,9 +121,9 @@ class DiagnosticManager {
other.Clear();
}

size_t Printf(DiagnosticSeverity severity, const char *format, ...)
size_t Printf(lldb::Severity severity, const char *format, ...)
__attribute__((format(printf, 3, 4)));
void PutString(DiagnosticSeverity severity, llvm::StringRef str);
void PutString(lldb::Severity severity, llvm::StringRef str);

void AppendMessageToDiagnostic(llvm::StringRef str) {
if (!m_diagnostics.empty())
Expand Down
2 changes: 1 addition & 1 deletion lldb/include/lldb/Host/Host.h
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ class Host {
lldb::pid_t pid);

/// Emit the given message to the operating system log.
static void SystemLog(llvm::StringRef message);
static void SystemLog(lldb::Severity severity, llvm::StringRef message);

/// Get the process ID for the calling process.
///
Expand Down
17 changes: 17 additions & 0 deletions lldb/include/lldb/Utility/Log.h
Original file line number Diff line number Diff line change
Expand Up @@ -112,6 +112,23 @@ class RotatingLogHandler : public LogHandler {
static char ID;
};

/// A T-style log handler that multiplexes messages to two log handlers.
class TeeLogHandler : public LogHandler {
public:
TeeLogHandler(std::shared_ptr<LogHandler> first_log_handler,
std::shared_ptr<LogHandler> second_log_handler);

void Emit(llvm::StringRef message) override;

bool isA(const void *ClassID) const override { return ClassID == &ID; }
static bool classof(const LogHandler *obj) { return obj->isA(&ID); }

private:
std::shared_ptr<LogHandler> m_first_log_handler;
std::shared_ptr<LogHandler> m_second_log_handler;
static char ID;
};

class Log final {
public:
/// The underlying type of all log channel enums. Declare them as:
Expand Down
7 changes: 7 additions & 0 deletions lldb/include/lldb/lldb-enumerations.h
Original file line number Diff line number Diff line change
Expand Up @@ -1371,6 +1371,13 @@ enum DebuggerBroadcastBit {
eBroadcastBitProgressCategory = (1 << 3),
};

/// Used for expressing severity in logs and diagnostics.
enum Severity {
eSeverityError,
eSeverityWarning,
eSeverityInfo, // Equivalent to Remark used in clang.
};

} // namespace lldb

#endif // LLDB_LLDB_ENUMERATIONS_H
40 changes: 20 additions & 20 deletions lldb/source/Core/Debugger.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1512,19 +1512,18 @@ void Debugger::ReportProgress(uint64_t progress_id, std::string title,
}
}

static void PrivateReportDiagnostic(Debugger &debugger,
DiagnosticEventData::Type type,
static void PrivateReportDiagnostic(Debugger &debugger, Severity severity,
std::string message,
bool debugger_specific) {
uint32_t event_type = 0;
switch (type) {
case DiagnosticEventData::Type::Info:
assert(false && "DiagnosticEventData::Type::Info should not be broadcast");
switch (severity) {
case eSeverityInfo:
assert(false && "eSeverityInfo should not be broadcast");
return;
case DiagnosticEventData::Type::Warning:
case eSeverityWarning:
event_type = Debugger::eBroadcastBitWarning;
break;
case DiagnosticEventData::Type::Error:
case eSeverityError:
event_type = Debugger::eBroadcastBitError;
break;
}
Expand All @@ -1533,29 +1532,32 @@ static void PrivateReportDiagnostic(Debugger &debugger,
if (!broadcaster.EventTypeHasListeners(event_type)) {
// Diagnostics are too important to drop. If nobody is listening, print the
// diagnostic directly to the debugger's error stream.
DiagnosticEventData event_data(type, std::move(message), debugger_specific);
DiagnosticEventData event_data(severity, std::move(message),
debugger_specific);
StreamSP stream = debugger.GetAsyncErrorStream();
event_data.Dump(stream.get());
return;
}
EventSP event_sp = std::make_shared<Event>(
event_type,
new DiagnosticEventData(type, std::move(message), debugger_specific));
new DiagnosticEventData(severity, std::move(message), debugger_specific));
broadcaster.BroadcastEvent(event_sp);
}

void Debugger::ReportDiagnosticImpl(DiagnosticEventData::Type type,
std::string message,
void Debugger::ReportDiagnosticImpl(Severity severity, std::string message,
std::optional<lldb::user_id_t> debugger_id,
std::once_flag *once) {
auto ReportDiagnosticLambda = [&]() {
// Always log diagnostics to the system log.
Host::SystemLog(severity, message);

// The diagnostic subsystem is optional but we still want to broadcast
// events when it's disabled.
if (Diagnostics::Enabled())
Diagnostics::Instance().Report(message);

// We don't broadcast info events.
if (type == DiagnosticEventData::Type::Info)
if (severity == lldb::eSeverityInfo)
return;

// Check if this diagnostic is for a specific debugger.
Expand All @@ -1564,15 +1566,16 @@ void Debugger::ReportDiagnosticImpl(DiagnosticEventData::Type type,
// still exists.
DebuggerSP debugger_sp = FindDebuggerWithID(*debugger_id);
if (debugger_sp)
PrivateReportDiagnostic(*debugger_sp, type, std::move(message), true);
PrivateReportDiagnostic(*debugger_sp, severity, std::move(message),
true);
return;
}
// The diagnostic event is not debugger specific, iterate over all debuggers
// and deliver a diagnostic event to each one.
if (g_debugger_list_ptr && g_debugger_list_mutex_ptr) {
std::lock_guard<std::recursive_mutex> guard(*g_debugger_list_mutex_ptr);
for (const auto &debugger : *g_debugger_list_ptr)
PrivateReportDiagnostic(*debugger, type, message, false);
PrivateReportDiagnostic(*debugger, severity, message, false);
}
};

Expand All @@ -1585,22 +1588,19 @@ void Debugger::ReportDiagnosticImpl(DiagnosticEventData::Type type,
void Debugger::ReportWarning(std::string message,
std::optional<lldb::user_id_t> debugger_id,
std::once_flag *once) {
ReportDiagnosticImpl(DiagnosticEventData::Type::Warning, std::move(message),
debugger_id, once);
ReportDiagnosticImpl(eSeverityWarning, std::move(message), debugger_id, once);
}

void Debugger::ReportError(std::string message,
std::optional<lldb::user_id_t> debugger_id,
std::once_flag *once) {
ReportDiagnosticImpl(DiagnosticEventData::Type::Error, std::move(message),
debugger_id, once);
ReportDiagnosticImpl(eSeverityError, std::move(message), debugger_id, once);
}

void Debugger::ReportInfo(std::string message,
std::optional<lldb::user_id_t> debugger_id,
std::once_flag *once) {
ReportDiagnosticImpl(DiagnosticEventData::Type::Info, std::move(message),
debugger_id, once);
ReportDiagnosticImpl(eSeverityInfo, std::move(message), debugger_id, once);
}

void Debugger::ReportSymbolChange(const ModuleSpec &module_spec) {
Expand Down
10 changes: 5 additions & 5 deletions lldb/source/Core/DebuggerEvents.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -73,19 +73,19 @@ ProgressEventData::GetAsStructuredData(const Event *event_ptr) {
}

llvm::StringRef DiagnosticEventData::GetPrefix() const {
switch (m_type) {
case Type::Info:
switch (m_severity) {
case Severity::eSeverityInfo:
return "info";
case Type::Warning:
case Severity::eSeverityWarning:
return "warning";
case Type::Error:
case Severity::eSeverityError:
return "error";
}
llvm_unreachable("Fully covered switch above!");
}

void DiagnosticEventData::Dump(Stream *s) const {
llvm::HighlightColor color = m_type == Type::Warning
llvm::HighlightColor color = m_severity == lldb::eSeverityWarning
? llvm::HighlightColor::Warning
: llvm::HighlightColor::Error;
llvm::WithColor(s->AsRawOstream(), color, llvm::ColorMode::Enable)
Expand Down
16 changes: 8 additions & 8 deletions lldb/source/Expression/DiagnosticManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,17 +31,17 @@ void DiagnosticManager::Dump(Log *log) {
log->PutCString(str.c_str());
}

static const char *StringForSeverity(DiagnosticSeverity severity) {
static const char *StringForSeverity(lldb::Severity severity) {
switch (severity) {
// this should be exhaustive
case lldb_private::eDiagnosticSeverityError:
case lldb::eSeverityError:
return "error: ";
case lldb_private::eDiagnosticSeverityWarning:
case lldb::eSeverityWarning:
return "warning: ";
case lldb_private::eDiagnosticSeverityRemark:
case lldb::eSeverityInfo:
return "";
}
llvm_unreachable("switch needs another case for DiagnosticSeverity enum");
llvm_unreachable("switch needs another case for lldb::Severity enum");
}

std::string DiagnosticManager::GetString(char separator) {
Expand All @@ -65,8 +65,8 @@ std::string DiagnosticManager::GetString(char separator) {
return ret;
}

size_t DiagnosticManager::Printf(DiagnosticSeverity severity,
const char *format, ...) {
size_t DiagnosticManager::Printf(lldb::Severity severity, const char *format,
...) {
StreamString ss;

va_list args;
Expand All @@ -79,7 +79,7 @@ size_t DiagnosticManager::Printf(DiagnosticSeverity severity,
return result;
}

void DiagnosticManager::PutString(DiagnosticSeverity severity,
void DiagnosticManager::PutString(lldb::Severity severity,
llvm::StringRef str) {
if (str.empty())
return;
Expand Down
Loading