Coverage Report

Created: 2023-09-12 09:32

/Users/buildslave/jenkins/workspace/coverage/llvm-project/lldb/include/lldb/Target/SystemRuntime.h
Line
Count
Source (jump to first uncovered line)
1
//===-- SystemRuntime.h -----------------------------------------*- C++ -*-===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
9
#ifndef LLDB_TARGET_SYSTEMRUNTIME_H
10
#define LLDB_TARGET_SYSTEMRUNTIME_H
11
12
#include <vector>
13
14
#include "lldb/Core/ModuleList.h"
15
#include "lldb/Core/PluginInterface.h"
16
#include "lldb/Target/QueueItem.h"
17
#include "lldb/Target/QueueList.h"
18
#include "lldb/Target/Runtime.h"
19
#include "lldb/Utility/ConstString.h"
20
#include "lldb/Utility/StructuredData.h"
21
#include "lldb/lldb-private.h"
22
#include "lldb/lldb-public.h"
23
24
namespace lldb_private {
25
26
/// \class SystemRuntime SystemRuntime.h "lldb/Target/SystemRuntime.h"
27
/// A plug-in interface definition class for system runtimes.
28
///
29
/// The system runtime plugins can collect information from the system
30
/// libraries during a Process' lifetime and provide information about how
31
/// objects/threads were originated.
32
///
33
/// For instance, a system runtime plugin use a breakpoint when threads are
34
/// created to record the backtrace of where that thread was created. Later,
35
/// when backtracing the created thread, it could extend the backtrace to show
36
/// where it was originally created from.
37
///
38
/// The plugin will insert its own breakpoint when Created and start
39
/// collecting information.  Later when it comes time to augment a Thread, it
40
/// can be asked to provide that information.
41
///
42
43
class SystemRuntime : public Runtime, public PluginInterface {
44
public:
45
  /// Find a system runtime plugin for a given process.
46
  ///
47
  /// Scans the installed SystemRuntime plugins and tries to find an instance
48
  /// that can be used to track image changes in \a process.
49
  ///
50
  /// \param[in] process
51
  ///     The process for which to try and locate a system runtime
52
  ///     plugin instance.
53
  static SystemRuntime *FindPlugin(Process *process);
54
55
  /// Construct with a process.
56
  SystemRuntime(Process *process);
57
58
  /// Destructor.
59
  ///
60
  /// The destructor is virtual since this class is designed to be inherited
61
  /// by the plug-in instance.
62
  ~SystemRuntime() override;
63
64
  /// Called after attaching to a process.
65
  ///
66
  /// Allow the SystemRuntime plugin to execute some code after attaching to a
67
  /// process.
68
  virtual void DidAttach();
69
70
  /// Called after launching a process.
71
  ///
72
  /// Allow the SystemRuntime plugin to execute some code after launching a
73
  /// process.
74
  virtual void DidLaunch();
75
76
  /// Called when modules have been loaded in the process.
77
  ///
78
  /// Allow the SystemRuntime plugin to enable logging features in the system
79
  /// runtime libraries.
80
  void ModulesDidLoad(const ModuleList &module_list) override;
81
82
  /// Called before detaching from a process.
83
  ///
84
  /// This will give a SystemRuntime plugin a chance to free any resources in
85
  /// the inferior process before we detach.
86
  virtual void Detach();
87
88
  /// Return a list of thread origin extended backtraces that may be
89
  /// available.
90
  ///
91
  /// A System Runtime may be able to provide a backtrace of when this
92
  /// thread was originally created.  Furthermore, it may be able to provide
93
  /// that extended backtrace for different styles of creation. On a system
94
  /// with both pthreads and libdispatch, aka Grand Central Dispatch, queues,
95
  /// the system runtime may be able to provide the pthread creation of the
96
  /// thread and it may also be able to provide the backtrace of when this GCD
97
  /// queue work block was enqueued. The caller may request these different
98
  /// origins by name.
99
  ///
100
  /// The names will be provided in the order that they are most likely to be
101
  /// requested.  For instance, a most natural order may be to request the GCD
102
  /// libdispatch queue origin.  If there is none, then request the pthread
103
  /// origin.
104
  ///
105
  /// \return
106
  ///   A vector of ConstStrings with names like "pthread" or "libdispatch".
107
  ///   An empty vector may be returned if no thread origin extended
108
  ///   backtrace capabilities are available.
109
  virtual const std::vector<ConstString> &GetExtendedBacktraceTypes();
110
111
  /// Return a Thread which shows the origin of this thread's creation.
112
  ///
113
  /// This likely returns a HistoryThread which shows how thread was
114
  /// originally created (e.g. "pthread" type), or how the work that is
115
  /// currently executing on it was originally enqueued (e.g. "libdispatch"
116
  /// type).
117
  ///
118
  /// There may be a chain of thread-origins; it may be informative to the end
119
  /// user to query the returned ThreadSP for its origins as well.
120
  ///
121
  /// \param [in] thread
122
  ///   The thread to examine.
123
  ///
124
  /// \param [in] type
125
  ///   The type of thread origin being requested.  The types supported
126
  ///   are returned from SystemRuntime::GetExtendedBacktraceTypes.
127
  ///
128
  /// \return
129
  ///   A ThreadSP which will have a StackList of frames.  This Thread will
130
  ///   not appear in the Process' list of current threads.  Normal thread
131
  ///   operations like stepping will not be available.  This is a historical
132
  ///   view thread and may be only useful for showing a backtrace.
133
  ///
134
  ///   An empty ThreadSP will be returned if no thread origin is available.
135
  virtual lldb::ThreadSP GetExtendedBacktraceThread(lldb::ThreadSP thread,
136
                                                    ConstString type);
137
138
  /// Get the extended backtrace thread for a QueueItem
139
  ///
140
  /// A QueueItem represents a function/block that will be executed on
141
  /// a libdispatch queue in the future, or it represents a function/block
142
  /// that is currently executing on a thread.
143
  ///
144
  /// This method will report a thread backtrace of the function that enqueued
145
  /// it originally, if possible.
146
  ///
147
  /// \param [in] queue_item_sp
148
  ///     The QueueItem that we are getting an extended backtrace for.
149
  ///
150
  /// \param [in] type
151
  ///     The type of extended backtrace to fetch.  The types supported
152
  ///     are returned from SystemRuntime::GetExtendedBacktraceTypes.
153
  ///
154
  /// \return
155
  ///     If an extended backtrace is available, it is returned.  Else
156
  ///     an empty ThreadSP is returned.
157
  virtual lldb::ThreadSP
158
  GetExtendedBacktraceForQueueItem(lldb::QueueItemSP queue_item_sp,
159
0
                                   ConstString type) {
160
0
    return lldb::ThreadSP();
161
0
  }
162
163
  /// Populate the Process' QueueList with libdispatch / GCD queues that
164
  /// exist.
165
  ///
166
  /// When process execution is paused, the SystemRuntime may be called to
167
  /// fill in the list of Queues that currently exist.
168
  ///
169
  /// \param [out] queue_list
170
  ///     This QueueList will be cleared, and any queues that currently exist
171
  ///     will be added.  An empty QueueList will be returned if no queues
172
  ///     exist or if this Systemruntime does not support libdispatch queues.
173
0
  virtual void PopulateQueueList(lldb_private::QueueList &queue_list) {}
174
175
  /// Get the queue name for a thread given a thread's dispatch_qaddr.
176
  ///
177
  /// On systems using libdispatch queues, a thread may be associated with a
178
  /// queue. There will be a call to get the thread's dispatch_qaddr.  At the
179
  /// dispatch_qaddr we will find the address of this thread's
180
  /// dispatch_queue_t structure. Given the address of the dispatch_queue_t
181
  /// structure for a thread, get the queue name and return it.
182
  ///
183
  /// \param [in] dispatch_qaddr
184
  ///     The address of the dispatch_qaddr pointer for this thread.
185
  ///
186
  /// \return
187
  ///     The string of this queue's name.  An empty string is returned if the
188
  ///     name could not be found.
189
  virtual std::string
190
0
  GetQueueNameFromThreadQAddress(lldb::addr_t dispatch_qaddr) {
191
0
    return "";
192
0
  }
193
194
  /// Get the QueueID for the libdispatch queue given the thread's
195
  /// dispatch_qaddr.
196
  ///
197
  /// On systems using libdispatch queues, a thread may be associated with a
198
  /// queue. There will be a call to get the thread's dispatch_qaddr.  At the
199
  /// dispatch_qaddr we will find the address of this thread's
200
  /// dispatch_queue_t structure. Given the address of the dispatch_queue_t
201
  /// structure for a thread, get the queue ID and return it.
202
  ///
203
  /// \param [in] dispatch_qaddr
204
  ///     The address of the dispatch_qaddr pointer for this thread.
205
  ///
206
  /// \return
207
  ///     The queue ID, or if it could not be retrieved, LLDB_INVALID_QUEUE_ID.
208
  virtual lldb::queue_id_t
209
0
  GetQueueIDFromThreadQAddress(lldb::addr_t dispatch_qaddr) {
210
0
    return LLDB_INVALID_QUEUE_ID;
211
0
  }
212
213
  /// Get the libdispatch_queue_t address for the queue given the thread's
214
  /// dispatch_qaddr.
215
  ///
216
  /// On systems using libdispatch queues, a thread may be associated with a
217
  /// queue. There will be a call to get the thread's dispatch_qaddr. Given
218
  /// the thread's dispatch_qaddr, find the libdispatch_queue_t address and
219
  /// return it.
220
  ///
221
  /// \param [in] dispatch_qaddr
222
  ///     The address of the dispatch_qaddr pointer for this thread.
223
  ///
224
  /// \return
225
  ///     The libdispatch_queue_t address, or LLDB_INVALID_ADDRESS if
226
  ///     unavailable/not found.
227
  virtual lldb::addr_t
228
0
  GetLibdispatchQueueAddressFromThreadQAddress(lldb::addr_t dispatch_qaddr) {
229
0
    return LLDB_INVALID_ADDRESS;
230
0
  }
231
232
  /// Retrieve the Queue kind for the queue at a thread's dispatch_qaddr.
233
  ///
234
  /// Retrieve the Queue kind - either eQueueKindSerial or
235
  /// eQueueKindConcurrent, indicating that this queue processes work items
236
  /// serially or concurrently.
237
  ///
238
  /// \return
239
  ///     The Queue kind, if it could be read, else eQueueKindUnknown.
240
0
  virtual lldb::QueueKind GetQueueKind(lldb::addr_t dispatch_qaddr) {
241
0
    return lldb::eQueueKindUnknown;
242
0
  }
243
244
  /// Get the pending work items for a libdispatch Queue
245
  ///
246
  /// If this system/process is using libdispatch and the runtime can do so,
247
  /// retrieve the list of pending work items for the specified Queue and add
248
  /// it to the Queue.
249
  ///
250
  /// \param [in] queue
251
  ///     The queue of interest.
252
0
  virtual void PopulatePendingItemsForQueue(lldb_private::Queue *queue) {}
253
254
  /// Complete the fields in a QueueItem
255
  ///
256
  /// PopulatePendingItemsForQueue() may not fill in all of the QueueItem
257
  /// details; when the remaining fields are needed, they will be fetched by
258
  /// call this method.
259
  ///
260
  /// \param [in] queue_item
261
  ///   The QueueItem that we will be completing.
262
  ///
263
  /// \param [in] item_ref
264
  ///     The item_ref token that is needed to retrieve the rest of the
265
  ///     information about the QueueItem.
266
  virtual void CompleteQueueItem(lldb_private::QueueItem *queue_item,
267
0
                                 lldb::addr_t item_ref) {}
268
269
  /// Add key-value pairs to the StructuredData dictionary object with
270
  /// information debugserver  may need when constructing the
271
  /// jThreadExtendedInfo packet.
272
  ///
273
  /// \param [out] dict
274
  ///     Dictionary to which key-value pairs should be added; they will
275
  ///     be sent to the remote gdb server stub as arguments in the
276
  ///     jThreadExtendedInfo request.
277
  virtual void AddThreadExtendedInfoPacketHints(
278
0
      lldb_private::StructuredData::ObjectSP dict) {}
279
280
  /// Determine whether it is safe to run an expression on a given thread
281
  ///
282
  /// If a system must not run functions on a thread in some particular state,
283
  /// this method gives a way for it to flag that the expression should not be
284
  /// run.
285
  ///
286
  /// \param [in] thread_sp
287
  ///     The thread we want to run the expression on.
288
  ///
289
  /// \return
290
  ///     True will be returned if there are no known problems with running an
291
  ///     expression on this thread.  False means that the inferior function
292
  ///     call should not be made on this thread.
293
0
  virtual bool SafeToCallFunctionsOnThisThread(lldb::ThreadSP thread_sp) {
294
0
    return true;
295
0
  }
296
297
protected:
298
  std::vector<ConstString> m_types;
299
300
private:
301
  SystemRuntime(const SystemRuntime &) = delete;
302
  const SystemRuntime &operator=(const SystemRuntime &) = delete;
303
};
304
305
} // namespace lldb_private
306
307
#endif // LLDB_TARGET_SYSTEMRUNTIME_H