wallace created this revision.
wallace added a reviewer: clayborg.
Herald added a subscriber: mgorny.
wallace requested review of this revision.
Herald added a project: LLDB.
Herald added a subscriber: lldb-commits.

Copying from the inline documentation:

  Trace exporter plug-ins operate on traces, converting the trace data provided 
by an \a lldb_private::TraceCursor into a different format that can be digested 
by other tools, e.g. Chrome Trace Event Profiler.
  Trace exporters are supposed to operate on an architecture-agnostic fashion, 
as a TraceCursor, which feeds the data, hides the actual trace technology being 
used.

I want to use this to make the code in https://reviews.llvm.org/D105741 a 
plug-in. I also imagine that there will be more and more exporters being 
implemented, as an exporter creates something useful out of trace data. And tbh 
I don't want to keep adding more stuff to the lldb/Target folder.

This is the minimal definition for a TraceExporter plugin. I plan to use this 
with the following commands:

- thread trace export <plug-in name> [plug-in specific args]
  - This command would support autocompletion of plug-in names
- thread trace export list
  - This command would list the available trace exporter plug-ins

I don't plan to create yet a "process trace export" because it's easier to 
start analyzing the trace of a given thread than of the entire process. When we 
need a process-level command, we can implement it.

I also don't plan to force each "export" command implementation to support 
multiple threads (for example, "thread trace start 1 2 3" or "thread trace 
start all" operate on many threads simultaneously). The reason is that the 
format used by the exporter might or might not support multiple threads, so I'm 
leaving this decision to each trace exporter plug-in.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D106501

Files:
  lldb/include/lldb/Core/PluginManager.h
  lldb/include/lldb/Target/TraceExporter.h
  lldb/include/lldb/lldb-forward.h
  lldb/include/lldb/lldb-private-interfaces.h
  lldb/source/Core/PluginManager.cpp
  lldb/source/Target/CMakeLists.txt
  lldb/source/Target/TraceExporter.cpp

Index: lldb/source/Target/TraceExporter.cpp
===================================================================
--- /dev/null
+++ lldb/source/Target/TraceExporter.cpp
@@ -0,0 +1,32 @@
+//===-- TraceExporter.cpp -------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "lldb/Target/TraceExporter.h"
+
+#include "lldb/Core/PluginManager.h"
+
+using namespace lldb;
+using namespace lldb_private;
+using namespace llvm;
+
+static Error createInvalidPlugInError(StringRef plugin_name) {
+  return createStringError(
+      std::errc::invalid_argument,
+      "no trace expoter plug-in matches the specified type: \"%s\"",
+      plugin_name.data());
+}
+
+Expected<lldb::TraceExporterSP>
+TraceExporter::FindPlugin(llvm::StringRef plugin_name) {
+  ConstString name(plugin_name);
+  if (auto create_callback =
+          PluginManager::GetTraceExporterCreateCallback(name))
+    return create_callback();
+
+  return createInvalidPlugInError(plugin_name);
+}
Index: lldb/source/Target/CMakeLists.txt
===================================================================
--- lldb/source/Target/CMakeLists.txt
+++ lldb/source/Target/CMakeLists.txt
@@ -68,6 +68,7 @@
   ThreadSpec.cpp
   Trace.cpp
   TraceCursor.cpp
+  TraceExporter.cpp
   TraceInstructionDumper.cpp
   UnixSignals.cpp
   UnwindAssembly.cpp
Index: lldb/source/Core/PluginManager.cpp
===================================================================
--- lldb/source/Core/PluginManager.cpp
+++ lldb/source/Core/PluginManager.cpp
@@ -1076,6 +1076,37 @@
   return llvm::StringRef();
 }
 
+#pragma mark TraceExporter
+
+typedef PluginInstance<TraceExporterCreateInstance> TraceExporterInstance;
+typedef PluginInstances<TraceExporterInstance> TraceExporterInstances;
+
+static TraceExporterInstances &GetTraceExporterInstances() {
+  static TraceExporterInstances g_instances;
+  return g_instances;
+}
+
+bool PluginManager::RegisterPlugin(
+    ConstString name, const char *description,
+    TraceExporterCreateInstance create_callback) {
+  return GetTraceExporterInstances().RegisterPlugin(name, description,
+                                                    create_callback);
+}
+
+bool PluginManager::UnregisterPlugin(
+    TraceExporterCreateInstance create_callback) {
+  return GetTraceExporterInstances().UnregisterPlugin(create_callback);
+}
+
+const char *
+PluginManager::GetTraceExporterPluginDescriptionAtIndex(uint32_t index) {
+  return GetTraceExporterInstances().GetDescriptionAtIndex(index);
+}
+
+const char *PluginManager::GetTraceExporterPluginNameAtIndex(uint32_t index) {
+  return GetTraceExporterInstances().GetNameAtIndex(index);
+}
+
 #pragma mark UnwindAssembly
 
 typedef PluginInstance<UnwindAssemblyCreateInstance> UnwindAssemblyInstance;
Index: lldb/include/lldb/lldb-private-interfaces.h
===================================================================
--- lldb/include/lldb/lldb-private-interfaces.h
+++ lldb/include/lldb/lldb-private-interfaces.h
@@ -118,6 +118,7 @@
     llvm::StringRef session_file_dir, lldb_private::Debugger &debugger);
 typedef llvm::Expected<lldb::TraceSP> (*TraceCreateInstanceForLiveProcess)(
     Process &process);
+typedef llvm::Expected<lldb::TraceExporterSP> (*TraceExporterCreateInstance)();
 } // namespace lldb_private
 
 #endif // #if defined(__cplusplus)
Index: lldb/include/lldb/lldb-forward.h
===================================================================
--- lldb/include/lldb/lldb-forward.h
+++ lldb/include/lldb/lldb-forward.h
@@ -230,6 +230,7 @@
 class ThreadPostMortemTrace;
 class Trace;
 class TraceCursor;
+class TraceExporter;
 class Type;
 class TypeAndOrName;
 class TypeCategoryImpl;
@@ -441,6 +442,7 @@
 typedef std::weak_ptr<lldb_private::ThreadPlan> ThreadPlanWP;
 typedef std::shared_ptr<lldb_private::ThreadPlanTracer> ThreadPlanTracerSP;
 typedef std::shared_ptr<lldb_private::Trace> TraceSP;
+typedef std::shared_ptr<lldb_private::TraceExporter> TraceExporterSP;
 typedef std::unique_ptr<lldb_private::TraceCursor> TraceCursorUP;
 typedef std::shared_ptr<lldb_private::Type> TypeSP;
 typedef std::weak_ptr<lldb_private::Type> TypeWP;
Index: lldb/include/lldb/Target/TraceExporter.h
===================================================================
--- /dev/null
+++ lldb/include/lldb/Target/TraceExporter.h
@@ -0,0 +1,46 @@
+//===-- TraceExporter.h -----------------------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLDB_TARGET_TRACE_EXPORTER_H
+#define LLDB_TARGET_TRACE_EXPORTER_H
+
+#include "lldb/Core/PluginInterface.h"
+
+namespace lldb_private {
+
+/// \class TraceExporter TraceExporter.h "lldb/Target/TraceExporter.h"
+/// A plug-in interface definition class for trace exporters.
+///
+/// Trace exporter plug-ins operate on traces, converting the trace data
+/// provided by an \a lldb_private::TraceCursor into a different format that can
+/// be digested by other tools, e.g. Chrome Trace Event Profiler.
+///
+/// Trace exporters are supposed to operate on an architecture-agnostic fashion,
+/// as a TraceCursor, which feeds the data, hides the actual trace technology
+/// being used.
+class TraceExporter : public PluginInterface {
+public:
+  /// Create an instance of a trace exporter plugin given its name.
+  ///
+  /// \param[in] plugin_Name
+  ///     Plug-in name to search.
+  ///
+  /// \return
+  ///     A \a TraceExporterSP instance, or an \a llvm::Error if the plug-in
+  ///     name doesn't match any registered plug-ins.
+  static llvm::Expected<lldb::TraceExporterSP>
+  FindPlugin(llvm::StringRef plugin_name);
+
+  /// Get the command handle for the "thread trace export" command.
+  virtual lldb::CommandObjectSP
+  GetThreadTraceExportCommand(CommandInterpreter &interpreter) = 0;
+};
+
+} // namespace lldb_private
+
+#endif // LLDB_TARGET_TRACE_EXPORTER_H
Index: lldb/include/lldb/Core/PluginManager.h
===================================================================
--- lldb/include/lldb/Core/PluginManager.h
+++ lldb/include/lldb/Core/PluginManager.h
@@ -369,6 +369,19 @@
   ///     number plugins, otherwise the actual schema is returned.
   static llvm::StringRef GetTraceSchema(size_t index);
 
+  // TraceExporter
+  static bool RegisterPlugin(ConstString name, const char *description,
+                             TraceExporterCreateInstance create_callback);
+
+  static bool UnregisterPlugin(TraceExporterCreateInstance create_callback);
+
+  static TraceExporterCreateInstance
+  GetTraceExporterCreateCallback(ConstString plugin_name);
+
+  static const char *GetTraceExporterPluginDescriptionAtIndex(uint32_t index);
+
+  static const char *GetTraceExporterPluginNameAtIndex(uint32_t index);
+
   // UnwindAssembly
   static bool RegisterPlugin(ConstString name, const char *description,
                              UnwindAssemblyCreateInstance create_callback);
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to