Fix executor hanging in some cases where tasks wake themselves.
This commit is contained in:
parent
53a064445f
commit
80ce73a2c1
1 changed files with 8 additions and 10 deletions
|
@ -110,18 +110,16 @@ impl Queue {
|
|||
}
|
||||
|
||||
unsafe fn dequeue_all(&self, on_task: impl Fn(*mut Header)) {
|
||||
loop {
|
||||
let mut task = self.head.swap(ptr::null_mut(), Ordering::AcqRel);
|
||||
let mut task = self.head.swap(ptr::null_mut(), Ordering::AcqRel);
|
||||
|
||||
if task.is_null() {
|
||||
// Queue is empty, we're done
|
||||
return;
|
||||
}
|
||||
while !task.is_null() {
|
||||
// If the task re-enqueues itself, the `next` pointer will get overwritten.
|
||||
// Therefore, first read the next pointer, and only then process the task.
|
||||
let next = (*task).next.load(Ordering::Relaxed);
|
||||
|
||||
while !task.is_null() {
|
||||
on_task(task);
|
||||
task = (*task).next.load(Ordering::Relaxed);
|
||||
}
|
||||
on_task(task);
|
||||
|
||||
task = next
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue