Skip to content

Commit 811e5ea

Browse files
authored
Fix another UB in raw dir (#474)
Signed-off-by: Alex Saveau <saveau.alexandre@gmail.com> Signed-off-by: Alex Saveau <saveau.alexandre@gmail.com>
1 parent a493c37 commit 811e5ea

File tree

2 files changed

+18
-14
lines changed

2 files changed

+18
-14
lines changed

src/fs/raw_dir.rs

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,8 @@ impl<'buf, Fd: AsFd> RawDir<'buf, Fd> {
4545
/// let fd = openat(cwd(), ".", OFlags::RDONLY | OFlags::DIRECTORY, Mode::empty()).unwrap();
4646
///
4747
/// let mut buf = Vec::with_capacity(8192);
48-
/// for entry in RawDir::new(fd, buf.spare_capacity_mut()) {
48+
/// let mut iter = RawDir::new(fd, buf.spare_capacity_mut());
49+
/// while let Some(entry) = iter.next() {
4950
/// let entry = entry.unwrap();
5051
/// dbg!(&entry);
5152
/// }
@@ -60,7 +61,8 @@ impl<'buf, Fd: AsFd> RawDir<'buf, Fd> {
6061
/// let fd = openat(cwd(), ".", OFlags::RDONLY | OFlags::DIRECTORY, Mode::empty()).unwrap();
6162
///
6263
/// let mut buf = [MaybeUninit::uninit(); 2048];
63-
/// for entry in RawDir::new(fd, &mut buf) {
64+
/// let mut iter = RawDir::new(fd, &mut buf);
65+
/// while let Some(entry) = iter.next() {
6466
/// let entry = entry.unwrap();
6567
/// dbg!(&entry);
6668
/// }
@@ -82,7 +84,8 @@ impl<'buf, Fd: AsFd> RawDir<'buf, Fd> {
8284
/// let mut buf = Vec::with_capacity(8192);
8385
/// 'read: loop {
8486
/// 'resize: {
85-
/// for entry in RawDir::new(&fd, buf.spare_capacity_mut()) {
87+
/// let mut iter = RawDir::new(&fd, buf.spare_capacity_mut());
88+
/// while let Some(entry) = iter.next() {
8689
/// let entry = match entry {
8790
/// Err(Errno::INVAL) => break 'resize,
8891
/// r => r.unwrap(),
@@ -162,11 +165,13 @@ impl<'a> RawDirEntry<'a> {
162165
}
163166
}
164167

165-
impl<'buf, Fd: AsFd> Iterator for RawDir<'buf, Fd> {
166-
type Item = io::Result<RawDirEntry<'buf>>;
167-
168+
impl<'buf, Fd: AsFd> RawDir<'buf, Fd> {
169+
/// Identical to [Iterator::next] except that [Iterator::Item] borrows from self.
170+
///
171+
/// Note: this interface will be broken to implement a stdlib iterator API with
172+
/// GAT support once one becomes available.
168173
#[allow(unsafe_code)]
169-
fn next(&mut self) -> Option<Self::Item> {
174+
pub fn next(&mut self) -> Option<io::Result<RawDirEntry>> {
170175
loop {
171176
if self.offset < self.initialized {
172177
let dirent_ptr = self.buf[self.offset..].as_ptr();

tests/fs/readdir.rs

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -56,24 +56,23 @@ fn read_entries(dir: &mut Dir) -> HashMap<String, DirEntry> {
5656

5757
#[cfg(any(target_os = "android", target_os = "linux"))]
5858
fn test_raw_dir(buf: &mut [MaybeUninit<u8>]) {
59+
use std::collections::HashSet;
5960
use std::io::{Seek, SeekFrom};
6061

6162
use rustix::fd::AsFd;
62-
use rustix::fs::{RawDir, RawDirEntry};
63+
use rustix::fs::RawDir;
6364

64-
fn read_raw_entries<'a, Fd: AsFd>(
65-
dir: &'a mut RawDir<'_, Fd>,
66-
) -> HashMap<String, RawDirEntry<'a>> {
67-
let mut out = HashMap::new();
68-
for entry in dir {
65+
fn read_raw_entries<Fd: AsFd>(dir: &mut RawDir<Fd>) -> HashSet<String> {
66+
let mut out = HashSet::new();
67+
while let Some(entry) = dir.next() {
6968
let entry = entry.expect("non-error entry");
7069
let name = entry
7170
.file_name()
7271
.to_str()
7372
.expect("utf8 filename")
7473
.to_owned();
7574
if name != "." && name != ".." {
76-
out.insert(name, entry);
75+
out.insert(name);
7776
}
7877
}
7978
out

0 commit comments

Comments
 (0)