From e7bd754231b5a92df70abbe5315f5653e252a323 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tymoteusz=20Wi=C5=9Bniewski?= Date: Sat, 18 Mar 2023 14:07:40 +0100 Subject: [PATCH] fs: fuse std iterator in `ReadDir` (#5555) Implementation of Tokio's ReadDir assumes that ReadDir from std is fused, but that's not the case on Windows. This change wraps the std iterator in std::iter::Fuse to make its usage correct. --- tokio/src/fs/read_dir.rs | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/tokio/src/fs/read_dir.rs b/tokio/src/fs/read_dir.rs index 9471e8ce809..3b30eb0aae3 100644 --- a/tokio/src/fs/read_dir.rs +++ b/tokio/src/fs/read_dir.rs @@ -33,7 +33,7 @@ const CHUNK_SIZE: usize = 32; pub async fn read_dir(path: impl AsRef) -> io::Result { let path = path.as_ref().to_owned(); asyncify(|| -> io::Result { - let mut std = std::fs::read_dir(path)?; + let mut std = std::fs::read_dir(path)?.fuse(); let mut buf = VecDeque::with_capacity(CHUNK_SIZE); ReadDir::next_chunk(&mut buf, &mut std); @@ -64,10 +64,12 @@ pub async fn read_dir(path: impl AsRef) -> io::Result { #[must_use = "streams do nothing unless polled"] pub struct ReadDir(State); +type StdReadDir = std::iter::Fuse; + #[derive(Debug)] enum State { - Idle(Option<(VecDeque>, std::fs::ReadDir)>), - Pending(JoinHandle<(VecDeque>, std::fs::ReadDir)>), + Idle(Option<(VecDeque>, StdReadDir)>), + Pending(JoinHandle<(VecDeque>, StdReadDir)>), } impl ReadDir { @@ -133,7 +135,7 @@ impl ReadDir { } } - fn next_chunk(buf: &mut VecDeque>, std: &mut std::fs::ReadDir) { + fn next_chunk(buf: &mut VecDeque>, std: &mut StdReadDir) { for ret in std.by_ref().take(CHUNK_SIZE) { let success = ret.is_ok();