Skip to content

Commit 264e4ac

Browse files
committed
Clear the active task immediately when suspending.
1 parent bd451f9 commit 264e4ac

File tree

3 files changed

+19
-9
lines changed

3 files changed

+19
-9
lines changed

stdlib/public/Concurrency/Actor.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -239,8 +239,8 @@ void swift::runJobInEstablishedExecutorContext(Job *job) {
239239

240240
task->runInFullyEstablishedContext();
241241

242-
// Clear the active task.
243-
ActiveTask::set(nullptr);
242+
assert(ActiveTask::get() == nullptr &&
243+
"active task wasn't cleared before susspending?");
244244
} else {
245245
// There's no extra bookkeeping to do for simple jobs.
246246
job->runSimpleInFullyEstablishedContext();
@@ -1937,6 +1937,7 @@ static void swift_task_switchImpl(SWIFT_ASYNC_CONTEXT AsyncContext *resumeContex
19371937
_swift_get_thread_id(), task, newExecutor.getIdentity());
19381938
#endif
19391939
task->flagAsSuspended();
1940+
_swift_task_clearCurrent();
19401941
swift_task_enqueue(task, newExecutor);
19411942
}
19421943

stdlib/public/Concurrency/Task.cpp

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,7 @@ FutureFragment::Status AsyncTask::waitFuture(AsyncTask *waitingTask,
124124
// Escalate the priority of this task based on the priority
125125
// of the waiting task.
126126
swift_task_escalate(this, waitingTask->Flags.getPriority());
127+
_swift_task_clearCurrent();
127128
return FutureFragment::Status::Executing;
128129
}
129130
}
@@ -937,7 +938,7 @@ size_t swift::swift_task_getJobFlags(AsyncTask *task) {
937938

938939
SWIFT_CC(swift)
939940
static AsyncTask *swift_task_suspendImpl() {
940-
auto task = swift_task_getCurrent();
941+
auto task = _swift_task_clearCurrent();
941942
task->flagAsSuspended();
942943
return task;
943944
}
@@ -963,16 +964,21 @@ static AsyncTask *swift_continuation_initImpl(ContinuationAsyncContext *context,
963964
: ContinuationStatus::Pending,
964965
std::memory_order_relaxed);
965966

966-
auto task = swift_task_getCurrent();
967-
assert(task && "initializing a continuation with no current task");
968-
task->ResumeContext = context;
969-
task->ResumeTask = context->ResumeParent;
967+
AsyncTask *task;
970968

971969
// A preawait immediately suspends the task.
972970
if (flags.isPreawaited()) {
971+
task = _swift_task_clearCurrent();
972+
assert(task && "initializing a continuation with no current task");
973973
task->flagAsSuspended();
974+
} else {
975+
task = swift_task_getCurrent();
976+
assert(task && "initializing a continuation with no current task");
974977
}
975978

979+
task->ResumeContext = context;
980+
task->ResumeTask = context->ResumeParent;
981+
976982
return task;
977983
}
978984

@@ -1016,7 +1022,10 @@ static void swift_continuation_awaitImpl(ContinuationAsyncContext *context) {
10161022
/*failure*/ std::memory_order_acquire);
10171023

10181024
// If that succeeded, we have nothing to do.
1019-
if (success) return;
1025+
if (success) {
1026+
_swift_task_clearCurrent();
1027+
return;
1028+
}
10201029

10211030
// If it failed, it should be because someone concurrently resumed
10221031
// (note that the compare-exchange above is strong).

stdlib/public/Concurrency/TaskGroup.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -810,10 +810,10 @@ PollResult TaskGroupImpl::poll(AsyncTask *waitingTask) {
810810
mutex.unlock(); // TODO: remove fragment lock, and use status for synchronization
811811
// no ready tasks, so we must wait.
812812
result.status = PollStatus::MustWait;
813+
_swift_task_clearCurrent();
813814
return result;
814815
} // else, try again
815816
}
816-
assert(false && "must successfully compare exchange the waiting task.");
817817
}
818818

819819
// =============================================================================

0 commit comments

Comments
 (0)