Skip to content

Commit f050b2a

Browse files
committed
Avoid deadlock in shared_timed_mutex on Windows
Signed-off-by: Dmitry Vodopyanov <[email protected]>
1 parent 096d0a0 commit f050b2a

File tree

2 files changed

+18
-4
lines changed

2 files changed

+18
-4
lines changed

sycl/source/detail/scheduler/scheduler.cpp

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,9 @@ EventImplPtr Scheduler::addCG(std::unique_ptr<detail::CG> CommandGroup,
6666
Command *NewCmd = nullptr;
6767
const bool IsKernel = CommandGroup->getType() == CG::KERNEL;
6868
{
69-
std::lock_guard<std::shared_timed_mutex> Lock(MGraphLock);
69+
std::unique_lock<std::shared_timed_mutex> Lock(MGraphLock, std::defer_lock);
70+
while (!Lock.try_lock())
71+
;
7072

7173
switch (CommandGroup->getType()) {
7274
case CG::UPDATE_HOST:
@@ -91,7 +93,9 @@ EventImplPtr Scheduler::addCG(std::unique_ptr<detail::CG> CommandGroup,
9193
}
9294

9395
EventImplPtr Scheduler::addCopyBack(Requirement *Req) {
94-
std::lock_guard<std::shared_timed_mutex> Lock(MGraphLock);
96+
std::unique_lock<std::shared_timed_mutex> Lock(MGraphLock, std::defer_lock);
97+
while (!Lock.try_lock())
98+
;
9599
Command *NewCmd = MGraphBuilder.addCopyBack(Req);
96100
// Command was not creted because there were no operations with
97101
// buffer.
@@ -147,7 +151,9 @@ void Scheduler::cleanupFinishedCommands(EventImplPtr FinishedEvent) {
147151
}
148152

149153
void Scheduler::removeMemoryObject(detail::SYCLMemObjI *MemObj) {
150-
std::lock_guard<std::shared_timed_mutex> Lock(MGraphLock);
154+
std::unique_lock<std::shared_timed_mutex> Lock(MGraphLock, std::defer_lock);
155+
while (!Lock.try_lock())
156+
;
151157

152158
MemObjRecord *Record = MGraphBuilder.getMemObjRecord(MemObj);
153159
if (!Record)
@@ -161,7 +167,13 @@ void Scheduler::removeMemoryObject(detail::SYCLMemObjI *MemObj) {
161167

162168
EventImplPtr Scheduler::addHostAccessor(Requirement *Req,
163169
const bool destructor) {
164-
std::lock_guard<std::shared_timed_mutex> Lock(MGraphLock);
170+
// Avoiding deadlock situation for MSVC. std::shared_timed_mutex specification
171+
// does not specify a priority for shared and exclusive locks. It will be a
172+
// deadlock in MSVC's std::shared_timed_mutex implementation, if exclusive
173+
// lock occurs after shared lock.
174+
std::unique_lock<std::shared_timed_mutex> Lock(MGraphLock, std::defer_lock);
175+
while (!Lock.try_lock())
176+
;
165177

166178
Command *NewCmd = MGraphBuilder.addHostAccessor(Req, destructor);
167179

sycl/source/detail/scheduler/scheduler.hpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -661,6 +661,8 @@ class Scheduler {
661661
void waitForRecordToFinish(MemObjRecord *Record);
662662

663663
GraphBuilder MGraphBuilder;
664+
// TODO: after switching to C++17, change std::shared_timed_mutex to
665+
// std::shared_mutex
664666
std::shared_timed_mutex MGraphLock;
665667

666668
QueueImplPtr DefaultHostQueue;

0 commit comments

Comments
 (0)