@@ -235,7 +235,7 @@ class DispatchHostTask {
235235 // Thus we employ read-lock of graph.
236236 {
237237 Scheduler &Sched = Scheduler::getInstance ();
238- std::shared_lock<std::shared_timed_mutex> Lock (Sched.MGraphLock );
238+ Scheduler::ReadLockT Lock (Sched.MGraphLock );
239239
240240 std::vector<DepDesc> Deps = MThisCmd->MDeps ;
241241
@@ -481,7 +481,7 @@ void Command::makeTraceEventEpilog() {
481481#endif
482482}
483483
484- void Command::processDepEvent (EventImplPtr DepEvent, const DepDesc &Dep) {
484+ Command * Command::processDepEvent (EventImplPtr DepEvent, const DepDesc &Dep) {
485485 const QueueImplPtr &WorkerQueue = getWorkerQueue ();
486486 const ContextImplPtr &WorkerContext = WorkerQueue->getContextImplPtr ();
487487
@@ -493,21 +493,25 @@ void Command::processDepEvent(EventImplPtr DepEvent, const DepDesc &Dep) {
493493 // call to waitInternal() is in waitForPreparedHostEvents() as it's called
494494 // from enqueue process functions
495495 MPreparedHostDepsEvents.push_back (DepEvent);
496- return ;
496+ return nullptr ;
497497 }
498498
499+ Command *ConnectionCmd = nullptr ;
500+
499501 // Do not add redundant event dependencies for in-order queues.
500502 if (Dep.MDepCommand && Dep.MDepCommand ->getWorkerQueue () == WorkerQueue &&
501503 WorkerQueue->has_property <property::queue::in_order>())
502- return ;
504+ return nullptr ;
503505
504506 ContextImplPtr DepEventContext = DepEvent->getContextImpl ();
505507 // If contexts don't match we'll connect them using host task
506508 if (DepEventContext != WorkerContext && !WorkerContext->is_host ()) {
507509 Scheduler::GraphBuilder &GB = Scheduler::getInstance ().MGraphBuilder ;
508- GB.connectDepEvent (this , DepEvent, Dep);
510+ ConnectionCmd = GB.connectDepEvent (this , DepEvent, Dep);
509511 } else
510512 MPreparedDepsEvents.push_back (std::move (DepEvent));
513+
514+ return ConnectionCmd;
511515}
512516
513517const ContextImplPtr &Command::getWorkerContext () const {
@@ -516,19 +520,23 @@ const ContextImplPtr &Command::getWorkerContext() const {
516520
517521const QueueImplPtr &Command::getWorkerQueue () const { return MQueue; }
518522
519- void Command::addDep (DepDesc NewDep) {
523+ Command *Command::addDep (DepDesc NewDep) {
524+ Command *ConnectionCmd = nullptr ;
525+
520526 if (NewDep.MDepCommand ) {
521- processDepEvent (NewDep.MDepCommand ->getEvent (), NewDep);
527+ ConnectionCmd = processDepEvent (NewDep.MDepCommand ->getEvent (), NewDep);
522528 }
523529 MDeps.push_back (NewDep);
524530#ifdef XPTI_ENABLE_INSTRUMENTATION
525531 emitEdgeEventForCommandDependence (
526532 NewDep.MDepCommand , (void *)NewDep.MDepRequirement ->MSYCLMemObj ,
527533 accessModeToString (NewDep.MDepRequirement ->MAccessMode ), true );
528534#endif
535+
536+ return ConnectionCmd;
529537}
530538
531- void Command::addDep (EventImplPtr Event) {
539+ Command * Command::addDep (EventImplPtr Event) {
532540#ifdef XPTI_ENABLE_INSTRUMENTATION
533541 // We need this for just the instrumentation, so guarding it will prevent
534542 // unused variable warnings when instrumentation is turned off
@@ -538,7 +546,7 @@ void Command::addDep(EventImplPtr Event) {
538546 emitEdgeEventForEventDependence (Cmd, PiEventAddr);
539547#endif
540548
541- processDepEvent (std::move (Event), DepDesc{nullptr , nullptr , nullptr });
549+ return processDepEvent (std::move (Event), DepDesc{nullptr , nullptr , nullptr });
542550}
543551
544552void Command::emitEnqueuedEventSignal (RT::PiEvent &PiEventAddr) {
@@ -732,7 +740,10 @@ AllocaCommand::AllocaCommand(QueueImplPtr Queue, Requirement Req,
732740 // Node event must be created before the dependent edge is added to this node,
733741 // so this call must be before the addDep() call.
734742 emitInstrumentationDataProxy ();
735- addDep (DepDesc (nullptr , getRequirement (), this ));
743+ // "Nothing to depend on"
744+ Command *ConnectionCmd = addDep (DepDesc (nullptr , getRequirement (), this ));
745+ assert (ConnectionCmd == nullptr );
746+ (void )ConnectionCmd;
736747}
737748
738749void AllocaCommand::emitInstrumentationData () {
@@ -795,7 +806,8 @@ void AllocaCommand::printDot(std::ostream &Stream) const {
795806}
796807
797808AllocaSubBufCommand::AllocaSubBufCommand (QueueImplPtr Queue, Requirement Req,
798- AllocaCommandBase *ParentAlloca)
809+ AllocaCommandBase *ParentAlloca,
810+ std::vector<Command *> &ToEnqueue)
799811 : AllocaCommandBase(CommandType::ALLOCA_SUB_BUF, std::move(Queue),
800812 std::move(Req),
801813 /* LinkedAllocaCmd*/ nullptr),
@@ -804,7 +816,10 @@ AllocaSubBufCommand::AllocaSubBufCommand(QueueImplPtr Queue, Requirement Req,
804816 // is added to this node, so this call must be before
805817 // the addDep() call.
806818 emitInstrumentationDataProxy ();
807- addDep (DepDesc (MParentAlloca, getRequirement (), MParentAlloca));
819+ Command *ConnectionCmd =
820+ addDep (DepDesc (MParentAlloca, getRequirement (), MParentAlloca));
821+ if (ConnectionCmd)
822+ ToEnqueue.push_back (ConnectionCmd);
808823}
809824
810825void AllocaSubBufCommand::emitInstrumentationData () {
@@ -1329,7 +1344,10 @@ void EmptyCommand::addRequirement(Command *DepCmd, AllocaCommandBase *AllocaCmd,
13291344 MRequirements.emplace_back (ReqRef);
13301345 const Requirement *const StoredReq = &MRequirements.back ();
13311346
1332- addDep (DepDesc{DepCmd, StoredReq, AllocaCmd});
1347+ // EmptyCommand is always host one, so we believe that result of addDep is nil
1348+ Command *Cmd = addDep (DepDesc{DepCmd, StoredReq, AllocaCmd});
1349+ assert (Cmd == nullptr && " Conection command should be null for EmptyCommand" );
1350+ (void )Cmd;
13331351}
13341352
13351353void EmptyCommand::emitInstrumentationData () {
0 commit comments