21 #ifdef XPTI_ENABLE_INSTRUMENTATION
22 #include "xpti/xpti_trace_framework.hpp"
29 inline namespace _V1 {
31 #ifdef XPTI_ENABLE_INSTRUMENTATION
32 extern xpti::trace_event_data_t *GSYCLGraphEvent;
69 "waitInternal method cannot be used for a discarded event.");
72 std::unique_lock<std::mutex> lock(
MMutex);
84 std::unique_lock<std::mutex> lock(
MMutex);
89 bool Succeeded =
MState.compare_exchange_strong(Expected, Desired);
91 assert(Succeeded &&
"Unexpected state of event");
100 assert(
false &&
"setComplete is not supported for non-host event");
104 auto Timestamp = std::chrono::high_resolution_clock::now().time_since_epoch();
105 return std::chrono::duration_cast<std::chrono::nanoseconds>(Timestamp)
134 : MIsContextInitialized(true), MEvent(Event),
136 MIsFlushed(true), MState(HES_Complete) {
140 "The syclContext must match the OpenCL context "
141 "associated with the clEvent. " +
148 &TempContext,
nullptr);
149 if (
MContext->getHandleRef() != TempContext) {
151 "The syclContext must match the OpenCL context "
152 "associated with the clEvent. " +
166 if (Queue->is_host()) {
168 if (Queue->has_property<property::queue::enable_profiling>()) {
172 "Out of host memory " +
181 uint64_t &IId)
const {
182 void *TraceEvent =
nullptr;
183 #ifdef XPTI_ENABLE_INSTRUMENTATION
184 constexpr uint16_t NotificationTraceType = xpti::trace_wait_begin;
185 if (!xptiCheckTraceEnabled(StreamID, NotificationTraceType))
189 static std::atomic<uint64_t> InstanceID = {1};
190 xpti::trace_event_data_t *WaitEvent =
nullptr;
194 xpti::utils::StringHelper SH;
205 WaitEvent = GSYCLGraphEvent;
209 xptiNotifySubscribers(StreamID, NotificationTraceType,
nullptr, WaitEvent,
210 IId,
static_cast<const void *
>(Name.c_str()));
211 TraceEvent = (
void *)WaitEvent;
218 int32_t StreamID, uint64_t IId)
const {
219 #ifdef XPTI_ENABLE_INSTRUMENTATION
220 constexpr uint16_t NotificationTraceType = xpti::trace_wait_end;
221 if (!(xptiCheckTraceEnabled(StreamID, NotificationTraceType) &&
225 xpti::trace_event_data_t *TraceEvent =
226 (xpti::trace_event_data_t *)TelemetryEvent;
227 xptiNotifySubscribers(StreamID, NotificationTraceType,
nullptr, TraceEvent,
228 IId,
static_cast<const void *
>(Name.c_str()));
235 "wait method cannot be used for a discarded event.");
239 "wait method cannot be used for an event associated "
240 "with a command graph.");
243 #ifdef XPTI_ENABLE_INSTRUMENTATION
244 void *TelemetryEvent =
nullptr;
258 #ifdef XPTI_ENABLE_INSTRUMENTATION
264 std::shared_ptr<sycl::detail::event_impl> Self) {
268 SubmittedQueue->throw_asynchronous();
272 std::weak_ptr<queue_impl> EmptyPtr;
274 if (!EmptyPtr.owner_before(
MQueue) && !
MQueue.owner_before(EmptyPtr)) {
276 "Profiling information is unavailable as the event "
277 "has no associated queue.");
282 "Profiling information is unavailable as the queue associated with "
283 "the event does not have the 'enable_profiling' property.");
289 event_impl::get_profiling_info<info::event_profiling::command_submit>() {
290 checkProfilingPreconditions();
306 if (MEventFromSubmittedExecCommandBuffer && !MHostEvent && MEvent) {
308 get_event_profiling_info<info::event_profiling::command_start>(
309 this->getHandleRef(), this->
getPlugin());
310 if (StartTime < MSubmitTime)
311 MSubmitTime = StartTime;
318 event_impl::get_profiling_info<info::event_profiling::command_start>() {
319 checkProfilingPreconditions();
322 if (isNOP() && MSubmitTime)
328 get_event_profiling_info<info::event_profiling::command_start>(
329 this->getHandleRef(), this->
getPlugin());
330 if (!MFallbackProfiling) {
333 auto DeviceBaseTime =
334 get_event_profiling_info<info::event_profiling::command_submit>(
335 this->getHandleRef(), this->
getPlugin());
336 return MHostBaseTime - DeviceBaseTime + StartTime;
341 if (!MHostProfilingInfo)
344 "Profiling info is not available. " +
346 return MHostProfilingInfo->getStartTime();
350 uint64_t event_impl::get_profiling_info<info::event_profiling::command_end>() {
351 checkProfilingPreconditions();
354 if (isNOP() && MSubmitTime)
360 get_event_profiling_info<info::event_profiling::command_end>(
361 this->getHandleRef(), this->
getPlugin());
362 if (!MFallbackProfiling) {
365 auto DeviceBaseTime =
366 get_event_profiling_info<info::event_profiling::command_submit>(
367 this->getHandleRef(), this->
getPlugin());
368 return MHostBaseTime - DeviceBaseTime + EndTime;
373 if (!MHostProfilingInfo)
376 "Profiling info is not available. " +
378 return MHostProfilingInfo->getEndTime();
381 template <> uint32_t event_impl::get_info<info::event::reference_count>() {
382 if (!MHostEvent && MEvent) {
383 return get_event_info<info::event::reference_count>(this->getHandleRef(),
391 event_impl::get_info<info::event::command_execution_status>() {
392 if (MState == HES_Discarded)
398 return get_event_info<info::event::command_execution_status>(
399 this->getHandleRef(), this->
getPlugin());
402 return sycl::info::event_command_status::submitted;
405 return MHostEvent && MState.load() != HES_Complete
406 ? sycl::info::event_command_status::submitted
420 auto TempContext =
MContext.get()->getHandleRef();
434 "get_wait_list() cannot be used for a discarded event.");
436 std::lock_guard<std::mutex> Lock(
MMutex);
438 std::vector<EventImplPtr> Result;
461 if (Queue == UserQueue)
476 std::lock_guard<std::mutex> Lock(
MMutex);
482 std::lock_guard<std::mutex> Lock(
MMutex);
484 Event->cleanupDependencyEvents();
487 Event->cleanupDependencyEvents();
497 MSubmitTime = Queue->getDeviceImplPtr()->getCurrentDeviceTime();
499 if (e.
code() == sycl::errc::feature_not_supported)
502 std::string(
"Unable to get command group submission time: ") +
504 std::rethrow_exception(std::current_exception());
525 return get_info<info::event::command_execution_status>() ==
The context class represents a SYCL context on which kernel functions may be executed.
The Command class represents some action that needs to be performed on one or more memory objects.
void * MTraceEvent
The event for node_create and task_begin.
Profiling info for the host execution.
void end()
Measures event's end time.
void start()
Measures event's start time.
void waitForEvent(const EventImplPtr &Event)
Waits for the event.
QueueImplPtr getDefaultHostQueue()
static Scheduler & getInstance()
void checkProfilingPreconditions() const
std::vector< EventImplPtr > getWaitList()
Returns vector of event_impl that this event_impl depends on.
void * instrumentationProlog(std::string &Name, int32_t StreamID, uint64_t &instance_id) const
uint64_t getSubmissionTime()
std::vector< EventImplPtr > MPostCompleteEvents
void cleanDepEventsThroughOneLevel()
Cleans dependencies of this event's dependencies.
void setComplete()
Marks this event as completed.
pi_native_handle getNative()
Gets the native handle of the SYCL event.
std::unique_ptr< HostProfilingInfo > MHostProfilingInfo
void setContextImpl(const ContextImplPtr &Context)
Associate event with the context.
void setHostEnqueueTime()
Calling this function to capture the host timestamp to use profiling base time.
std::weak_ptr< ext::oneapi::experimental::detail::graph_impl > MGraph
Store the command graph associated with this event, if any.
const ContextImplPtr & getContextImpl()
Returns context that is associated with this event.
void flushIfNeeded(const QueueImplPtr &UserQueue)
Performs a flush on the queue associated with this event if the user queue is different and the task ...
std::weak_ptr< queue_impl > MSubmittedQueue
bool MIsContextInitialized
std::atomic< int > MState
sycl::detail::pi::PiEvent MEvent
void ensureContextInitialized()
void instrumentationEpilog(void *TelementryEvent, const std::string &Name, int32_t StreamID, uint64_t IId) const
event_impl(std::optional< HostEventState > State=HES_Complete)
Constructs a ready SYCL event.
void associateWithQueue(const QueueImplPtr &Queue)
Associate event with provided queue.
bool isCompleted()
Checks if this event is complete.
std::vector< EventImplPtr > MPreparedHostDepsEvents
void setStateIncomplete()
Clear the event state.
std::condition_variable cv
void waitInternal()
Waits for the event with respect to device type.
std::vector< EventImplPtr > MPreparedDepsEvents
Dependency events prepared for waiting by backend.
void setSubmissionTime()
Calling this function queries the current device timestamp and sets it as submission time for the com...
void cleanupDependencyEvents()
Cleans dependencies of this event_impl.
void wait_and_throw(std::shared_ptr< sycl::detail::event_impl > Self)
Waits for the event.
void wait(std::shared_ptr< sycl::detail::event_impl > Self)
Waits for the event.
const PluginPtr & getPlugin()
sycl::detail::pi::PiEvent & getHandleRef()
Returns raw interoperability event handle.
bool is_host()
Checks if this event is a SYCL host event.
std::atomic< bool > MIsFlushed
Indicates that the task associated with this event has been submitted by the queue to the device.
std::weak_ptr< queue_impl > MQueue
static ContextImplPtr getDefaultOrNew(const DeviceImplPtr &Device)
The SYCL device class encapsulates a single SYCL device on which kernels may be executed.
const char * what() const noexcept final
const std::error_code & code() const noexcept
constexpr const char * SYCL_STREAM_NAME
std::string codeToString(pi_int32 code)
static uint64_t getTimestamp()
std::shared_ptr< sycl::detail::context_impl > ContextImplPtr
static const PluginPtr & getPlugin(backend Backend)
decltype(Obj::impl) getSyclObjImpl(const Obj &SyclObject)
std::shared_ptr< event_impl > EventImplPtr
std::shared_ptr< plugin > PluginPtr
std::shared_ptr< sycl::detail::queue_impl > QueueImplPtr
std::error_code make_error_code(sycl::errc E) noexcept
Constructs an error code using e and sycl_category()
uintptr_t pi_native_handle
pi_result piextEventGetNativeHandle(pi_event event, pi_native_handle *nativeHandle)
Gets the native handle of a PI event object.
pi_result piEventGetInfo(pi_event event, pi_event_info param_name, size_t param_value_size, void *param_value, size_t *param_value_size_ret)
@ PI_EVENT_INFO_COMMAND_EXECUTION_STATUS
pi_result piEventsWait(pi_uint32 num_events, const pi_event *event_list)
pi_result piQueueFlush(pi_queue command_queue)
pi_result piEventRelease(pi_event event)
pi_result piEventRetain(pi_event event)
decltype(piEventCreate) piEventCreate