@@ -577,7 +577,6 @@ TaskGroupTaskStatusRecord * TaskGroup::getTaskRecord() {
577
577
// Initializes into the preallocated _group an actual TaskGroupImpl.
578
578
SWIFT_CC (swift)
579
579
static void swift_taskGroup_initializeImpl(TaskGroup *group, const Metadata *T) {
580
- fprintf (stderr, " [%s:%d](%s) INITIALIZE...\n " , __FILE_NAME__, __LINE__, __FUNCTION__);
581
580
swift_taskGroup_initializeWithFlags (0 , group, T);
582
581
}
583
582
@@ -588,9 +587,6 @@ static void swift_taskGroup_initializeWithFlagsImpl(size_t rawGroupFlags, TaskGr
588
587
589
588
TaskGroupFlags groupFlags (rawGroupFlags);
590
589
591
- fprintf (stderr, " [%s:%d](%s) INITIALIZE FLAGS: flags.discardResults:%d\n " , __FILE_NAME__, __LINE__, __FUNCTION__,
592
- groupFlags.isDiscardResults ());
593
-
594
590
TaskGroupImpl *impl = ::new (group)
595
591
TaskGroupImpl (T, groupFlags.isDiscardResults ());
596
592
auto record = impl->getTaskRecord ();
@@ -809,23 +805,28 @@ void TaskGroupImpl::offer(AsyncTask *completedTask, AsyncContext *context) {
809
805
// and we immediately discard the result.
810
806
SWIFT_TASK_GROUP_DEBUG_LOG (this , " discard result, hadError:%d, was pending:%llu" ,
811
807
hadErrorResult, assumed.pendingTasks (this ));
812
- if (!lastPendingTaskAndWaitingTask) {
813
- // we're not able to immediately complete a waitingTask with this task, so we may have to store it...
814
- if (hadErrorResult && readyQueue.isEmpty ()) {
815
- // a discardResults throwing task group must retain the FIRST error it encounters.
816
- SWIFT_TASK_GROUP_DEBUG_LOG (this , " offer error, completedTask:%p" , completedTask);
817
- enqueueCompletedTask (completedTask, /* hadErrorResult=*/ hadErrorResult);
818
- }
819
- } // else, no need to store the task, as we'll immediately complete the waitingTask using it.
820
-
821
808
// If this was the last pending task, and there is a waiting task (from waitAll),
822
809
// we must resume the task; but not otherwise. There cannot be any waiters on next()
823
810
// while we're discarding results.
824
811
if (lastPendingTaskAndWaitingTask) {
812
+ ReadyQueueItem item;
813
+ bool dequeuedErrorItem = readyQueue.dequeue (item);
825
814
SWIFT_TASK_GROUP_DEBUG_LOG (this , " offer, offered last pending task, resume waiting task:%p" ,
826
815
waitQueue.load (std::memory_order_relaxed));
827
- resumeWaitingTask (completedTask, assumed, /* hadErrorResult=*/ hadErrorResult);
816
+ if (dequeuedErrorItem) {
817
+ assert (item.getStatus () == ReadyStatus::Error && " only errors can be stored by a discarding task group, yet it wasn't an error!" );
818
+ resumeWaitingTask (item.getTask (), assumed, /* hadErrorResult=*/ true );
819
+ } else {
820
+ resumeWaitingTask (completedTask, assumed, /* hadErrorResult=*/ hadErrorResult);
821
+ }
828
822
} else {
823
+ assert (!lastPendingTaskAndWaitingTask);
824
+ if (hadErrorResult && readyQueue.isEmpty ()) {
825
+ // a discardResults throwing task group must retain the FIRST error it encounters.
826
+ SWIFT_TASK_GROUP_DEBUG_LOG (this , " offer error, completedTask:%p" , completedTask);
827
+ enqueueCompletedTask (completedTask, /* hadErrorResult=*/ hadErrorResult);
828
+ } // else, we just are going to discard it.
829
+
829
830
auto afterComplete = statusCompletePendingAssumeRelease ();
830
831
SWIFT_TASK_GROUP_DEBUG_LOG (this , " offer, either more pending tasks, or no waiting task, status:%s" ,
831
832
afterComplete.to_string (this ).c_str ());
0 commit comments