当您调用标准库的频道接收或 try_recv 方法时,Tokio 的 run_queue 会发生什么?

What happens in Tokio's run_queue when you call the standard library's channel recv or try_recv methods?

我不确定如果您在以下情况下使用 standard library's channel implementation 会发生什么情况。

案例一

let (tx, rx) = std::sync::mpsc::unbounded_channel();

// some code where multiple producers are sending data through tx
tokio::spawn(async move {
    while let Some(message) = rx.recv().await {
        //do something with message
    }
})

案例二

let (tx, rx) = std::sync::mpsc::unbounded_channel();

// some code where multiple producers are sending data through tx
tokio::spawn(async move {
    while let Some(message) = rx.try_recv().await {
        //do something with message }
    }
})

在这两种情况下,当通道为空并且接收者正在等待一些消息时,情况 1 中的 Tokio 任务是否会留在 run_queue 中,因为 recv() 正在阻塞?

另一方面,由于 try_recv() 没有阻塞,Tokio 任务是否会离开 运行 队列,以便线程可以在没有消息可读时执行其他任务?

深入研究源代码后,我的结论是,当 Tokio 频道等待消息时,它们会被移出 运行 队列。使用 Tokio 时,在接收器上调用 recv() 永远不会成为阻塞代码。

我也怀疑 futures::stream::stream::poll_next() 是否会阻塞,但与 Tokio 频道一样,当某些值可用时它们会被唤醒。