DPC++ Runtime
Runtime libraries for oneAPI DPC++
xpti_registry.hpp
Go to the documentation of this file.
1 //==---------- xpti_registry.hpp ----- XPTI Stream Registry ----------------==//
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 #pragma once
10 
11 #include <mutex>
12 #include <string>
13 #include <unordered_set>
14 
15 #include <sycl/detail/common.hpp>
16 #include <sycl/version.hpp>
17 
18 #ifdef XPTI_ENABLE_INSTRUMENTATION
19 // Include the headers necessary for emitting
20 // traces using the trace framework
21 #include "xpti/xpti_trace_framework.hpp"
22 #endif
23 
24 namespace sycl {
25 inline namespace _V1 {
26 namespace detail {
27 // We define a sycl stream name and this will be used by the instrumentation
28 // framework
29 inline constexpr const char *SYCL_STREAM_NAME = "sycl";
30 // Stream name being used for traces generated from the SYCL plugin layer
31 inline constexpr const char *SYCL_PICALL_STREAM_NAME = "sycl.pi";
32 // Stream name being used for traces generated from PI calls. This stream
33 // contains information about function arguments.
34 inline constexpr const char *SYCL_PIDEBUGCALL_STREAM_NAME = "sycl.pi.debug";
35 inline constexpr auto SYCL_MEM_ALLOC_STREAM_NAME =
36  "sycl.experimental.mem_alloc";
37 
38 #ifdef XPTI_ENABLE_INSTRUMENTATION
39 extern uint8_t GBufferStreamID;
40 extern uint8_t GImageStreamID;
41 extern uint8_t GMemAllocStreamID;
42 extern xpti::trace_event_data_t *GMemAllocEvent;
43 extern xpti::trace_event_data_t *GSYCLGraphEvent;
44 
45 #define STR(x) #x
46 #define SYCL_VERSION_STR \
47  "sycl " STR(__LIBSYCL_MAJOR_VERSION) "." STR(__LIBSYCL_MINOR_VERSION)
48 
51 constexpr uint32_t GMajVer = __LIBSYCL_MAJOR_VERSION;
52 constexpr uint32_t GMinVer = __LIBSYCL_MINOR_VERSION;
53 constexpr const char *GVerStr = SYCL_VERSION_STR;
54 #endif
55 
56 // Stream name being used to notify about buffer objects.
57 inline constexpr const char *SYCL_BUFFER_STREAM_NAME =
58  "sycl.experimental.buffer";
59 
60 // Stream name being used to notify about image objects.
61 inline constexpr const char *SYCL_IMAGE_STREAM_NAME = "sycl.experimental.image";
62 
63 class XPTIRegistry {
64 public:
66 #ifdef XPTI_ENABLE_INSTRUMENTATION
67  std::call_once(MInitialized, [this] {
68  xptiFrameworkInitialize();
69  // SYCL buffer events
70  GBufferStreamID = xptiRegisterStream(SYCL_BUFFER_STREAM_NAME);
71  this->initializeStream(SYCL_BUFFER_STREAM_NAME, 0, 1, "0.1");
72  // SYCL image events
73  GImageStreamID = xptiRegisterStream(SYCL_IMAGE_STREAM_NAME);
74  this->initializeStream(SYCL_IMAGE_STREAM_NAME, 0, 1, "0.1");
75 
76  // Memory allocation events
77  GMemAllocStreamID = xptiRegisterStream(SYCL_MEM_ALLOC_STREAM_NAME);
78  this->initializeStream(SYCL_MEM_ALLOC_STREAM_NAME, 0, 1, "0.1");
79  xpti::payload_t MAPayload("SYCL Memory Allocations Layer");
80  uint64_t MAInstanceNo = 0;
81  GMemAllocEvent = xptiMakeEvent("SYCL Memory Allocations", &MAPayload,
82  xpti::trace_algorithm_event,
83  xpti_at::active, &MAInstanceNo);
84  });
85 #endif
86  }
87 
94  void initializeStream(const std::string &StreamName, uint32_t MajVer,
95  uint32_t MinVer, const std::string &VerStr) {
96 #ifdef XPTI_ENABLE_INSTRUMENTATION
97  MActiveStreams.insert(StreamName);
98  xptiInitialize(StreamName.c_str(), MajVer, MinVer, VerStr.c_str());
99 #endif // XPTI_ENABLE_INSTRUMENTATION
100  }
101 
103 #ifdef XPTI_ENABLE_INSTRUMENTATION
104  for (const auto &StreamName : MActiveStreams) {
105  xptiFinalize(StreamName.c_str());
106  }
107  xptiFrameworkFinalize();
108 #endif // XPTI_ENABLE_INSTRUMENTATION
109  }
110 
111  static void bufferConstructorNotification(const void *,
112  const detail::code_location &,
113  const void *, const void *,
114  uint32_t, uint32_t, size_t[3]);
115  static void bufferAssociateNotification(const void *, const void *);
116  static void bufferReleaseNotification(const void *, const void *);
117  static void bufferDestructorNotification(const void *);
118  static void bufferAccessorNotification(const void *, const void *, uint32_t,
119  uint32_t,
120  const detail::code_location &);
121 
122  static void sampledImageConstructorNotification(const void *,
123  const detail::code_location &,
124  const void *, uint32_t,
125  size_t[3], uint32_t, uint32_t,
126  uint32_t, uint32_t);
127  static void sampledImageDestructorNotification(const void *);
128 
130  const void *, const detail::code_location &, const void *, uint32_t,
131  size_t[3], uint32_t);
132  static void unsampledImageDestructorNotification(const void *);
133 
134  static void unsampledImageAccessorNotification(const void *, const void *,
135  uint32_t, uint32_t,
136  const void *, uint32_t,
137  const detail::code_location &);
138  static void
139  unsampledImageHostAccessorNotification(const void *, const void *, uint32_t,
140  const void *, uint32_t,
141  const detail::code_location &);
142  static void sampledImageAccessorNotification(const void *, const void *,
143  uint32_t, const void *, uint32_t,
144  const detail::code_location &);
145  static void
146  sampledImageHostAccessorNotification(const void *, const void *, const void *,
147  uint32_t, const detail::code_location &);
148 
149 private:
150  std::unordered_set<std::string> MActiveStreams;
151  std::once_flag MInitialized;
152 
153 #ifdef XPTI_ENABLE_INSTRUMENTATION
154  static xpti::trace_event_data_t *
155  createTraceEvent(const void *Obj, const void *ObjName, uint64_t &IId,
156  const detail::code_location &CodeLoc,
157  uint16_t TraceEventType);
158 #endif // XPTI_ENABLE_INSTRUMENTATION
159 };
160 
164 #if XPTI_ENABLE_INSTRUMENTATION
165 class XPTIScope {
166 public:
167  using TracePoint = xpti::framework::tracepoint_t;
175  XPTIScope(void *CodePtr, uint16_t TraceType, const char *StreamName,
176  const char *UserData)
177  : MUserData(UserData), MStreamID(0), MInstanceID(0), MScopedNotify(false),
178  MTraceType(0) {
180  auto TData = Tls.query();
181  // If TLS is not set, we can still genertate universal IDs with user data
182  // and CodePtr information
183  const char *FuncName = TData.functionName();
184  if (!TData.functionName() && !TData.fileName())
185  FuncName = UserData;
186  // Create a tracepoint object that has a lifetime of this class
187  MTP = new TracePoint(TData.fileName(), FuncName, TData.lineNumber(),
188  TData.columnNumber(), CodePtr);
189  if (TraceType == (uint16_t)xpti::trace_point_type_t::graph_create ||
190  TraceType == (uint16_t)xpti::trace_point_type_t::node_create ||
191  TraceType == (uint16_t)xpti::trace_point_type_t::edge_create)
192  MTP->parent_event(GSYCLGraphEvent);
193  // Now if tracing is enabled, create trace events and notify
194  if (xptiTraceEnabled() && MTP) {
195  MTP->stream(StreamName).trace_type((xpti::trace_point_type_t)TraceType);
196  MTraceEvent = const_cast<xpti::trace_event_data_t *>(MTP->trace_event());
197  MStreamID = MTP->stream_id();
198  MInstanceID = MTP->instance_id();
199  }
200  }
201 
202  XPTIScope(const XPTIScope &rhs) = delete;
203 
204  XPTIScope &operator=(const XPTIScope &rhs) = delete;
205 
206  xpti::trace_event_data_t *traceEvent() { return MTraceEvent; }
207 
208  uint8_t streamID() { return MStreamID; }
209 
210  uint64_t instanceID() { return MTP ? MTP->instance_id() : 0; }
211 
212  XPTIScope &
213  addMetadata(const std::function<void(xpti::trace_event_data_t *)> &Callback) {
214  if (xptiTraceEnabled() && MTP) {
215  auto TEvent = const_cast<xpti::trace_event_data_t *>(MTP->trace_event());
216  Callback(TEvent);
217  }
218  return *this;
219  }
220 
221  XPTIScope &notify() {
222  MTP->notify(static_cast<const void *>(MUserData));
223  return *this;
224  }
225 
228  XPTIScope &scopedNotify(uint16_t TraceType) {
229  // Keep this data even if no subscribers are for this TraceType (begin).
230  // Someone could still use (end) emitted from destructor.
231  MTraceType = TraceType & 0xfffe;
232  MScopedNotify = true;
233  if (xptiCheckTraceEnabled(MStreamID, TraceType) && MTP) {
234  xptiNotifySubscribers(MStreamID, MTraceType, nullptr, MTraceEvent,
235  MInstanceID, static_cast<const void *>(MUserData));
236  }
237  return *this;
238  }
239  ~XPTIScope() {
240  MTraceType = MTraceType | 1;
241  if (xptiCheckTraceEnabled(MStreamID, MTraceType) && MTP && MScopedNotify) {
242  if (MTraceType == (uint16_t)xpti::trace_point_type_t::signal ||
243  MTraceType == (uint16_t)xpti::trace_point_type_t::graph_create ||
244  MTraceType == (uint16_t)xpti::trace_point_type_t::node_create ||
245  MTraceType == (uint16_t)xpti::trace_point_type_t::edge_create ||
246  MTraceType == (uint16_t)xpti::trace_point_type_t::diagnostics)
247  return;
248 
249  // Only notify for a trace type that has a begin/end
250  xptiNotifySubscribers(MStreamID, MTraceType, nullptr, MTraceEvent,
251  MInstanceID, static_cast<const void *>(MUserData));
252  }
253  // Delete the tracepoint object which will clear TLS if it is the top of
254  // the scope
255  delete MTP;
256  }
257 
258 private:
259  // Tracepoint_t object who's lifetime is that of the class
260  TracePoint *MTP = nullptr;
261  // Trace event created from the TLS data, if it exists
262  xpti::trace_event_data_t *MTraceEvent = nullptr;
263  // The const string that indicates the operation
264  const char *MUserData = nullptr;
265  // The stream on which the notifications occur
266  uint8_t MStreamID;
267  // The instance ID for the trace event; if it is called in a loop, then the
268  // trace event ID will remain the same, but the instance ID will increment
269  uint64_t MInstanceID;
270  // If scoped notifcation is requested, this tracks the request
271  bool MScopedNotify;
272  // The trace type information for scoped notifications
273  uint16_t MTraceType;
274 }; // class XPTIScope
275 #endif
276 
277 } // namespace detail
278 } // namespace _V1
279 } // namespace sycl
static void sampledImageHostAccessorNotification(const void *, const void *, const void *, uint32_t, const detail::code_location &)
static void bufferAccessorNotification(const void *, const void *, uint32_t, uint32_t, const detail::code_location &)
static void bufferAssociateNotification(const void *, const void *)
static void unsampledImageAccessorNotification(const void *, const void *, uint32_t, uint32_t, const void *, uint32_t, const detail::code_location &)
static void bufferConstructorNotification(const void *, const detail::code_location &, const void *, const void *, uint32_t, uint32_t, size_t[3])
static void unsampledImageHostAccessorNotification(const void *, const void *, uint32_t, const void *, uint32_t, const detail::code_location &)
static void sampledImageDestructorNotification(const void *)
static void unsampledImageDestructorNotification(const void *)
static void bufferDestructorNotification(const void *)
static void sampledImageAccessorNotification(const void *, const void *, uint32_t, const void *, uint32_t, const detail::code_location &)
static void bufferReleaseNotification(const void *, const void *)
static void unsampledImageConstructorNotification(const void *, const detail::code_location &, const void *, uint32_t, size_t[3], uint32_t)
void initializeStream(const std::string &StreamName, uint32_t MajVer, uint32_t MinVer, const std::string &VerStr)
Notifies XPTI subscribers about new stream.
static void sampledImageConstructorNotification(const void *, const detail::code_location &, const void *, uint32_t, size_t[3], uint32_t, uint32_t, uint32_t, uint32_t)
Data type that manages the code_location information in TLS.
Definition: common.hpp:129
const detail::code_location & query()
Query the information in the TLS slot.
Definition: common.cpp:55
constexpr const char * SYCL_IMAGE_STREAM_NAME
constexpr const char * SYCL_PIDEBUGCALL_STREAM_NAME
constexpr const char * SYCL_STREAM_NAME
constexpr auto SYCL_MEM_ALLOC_STREAM_NAME
constexpr const char * SYCL_BUFFER_STREAM_NAME
constexpr const char * SYCL_PICALL_STREAM_NAME
multi_ptr & operator=(const multi_ptr &)=default
Definition: access.hpp:18
constexpr const char * functionName() const noexcept
Definition: common.hpp:90
constexpr int GMajVer
Definition: tracing.cpp:27
constexpr int GMinVer
Definition: tracing.cpp:28
constexpr auto GVerStr
Definition: tracing.cpp:26