Skip to content

Commit e0ac250

Browse files
committed
revise the interpretation of ReadDir
HermitOS supports getdents64. As under Linux, the dirent64 entry `d_off` is not longer used, because its definition is not clear. Instead of `d_off` the entry `d_reclen` is used to determine the end of the dirent64 entry.
1 parent c672773 commit e0ac250

File tree

1 file changed

+8
-12
lines changed
  • library/std/src/sys/pal/hermit

1 file changed

+8
-12
lines changed

library/std/src/sys/pal/hermit/fs.rs

+8-12
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ impl InnerReadDir {
4747

4848
pub struct ReadDir {
4949
inner: Arc<InnerReadDir>,
50-
pos: i64,
50+
pos: usize,
5151
}
5252

5353
impl ReadDir {
@@ -197,38 +197,34 @@ impl Iterator for ReadDir {
197197

198198
fn next(&mut self) -> Option<io::Result<DirEntry>> {
199199
let mut counter: usize = 0;
200-
let mut offset: i64 = 0;
200+
let mut offset: usize = 0;
201201

202202
// loop over all directory entries and search the entry for the current position
203203
loop {
204204
// leave function, if the loop reaches the of the buffer (with all entries)
205-
if offset >= self.inner.dir.len().try_into().unwrap() {
205+
if offset >= self.inner.dir.len() {
206206
return None;
207207
}
208208

209209
let dir = unsafe {
210-
&*(self.inner.dir.as_ptr().offset(offset.try_into().unwrap()) as *const dirent64)
210+
&*(self.inner.dir.as_ptr().add(offset) as *const dirent64)
211211
};
212212

213-
if counter == self.pos.try_into().unwrap() {
213+
if counter == self.pos {
214214
self.pos += 1;
215215

216216
// After dirent64, the file name is stored. d_reclen represents the length of the dirent64
217217
// plus the length of the file name. Consequently, file name has a size of d_reclen minus
218218
// the size of dirent64. The file name is always a C string and terminated by `\0`.
219219
// Consequently, we are able to ignore the last byte.
220220
let name_bytes = unsafe {
221-
core::slice::from_raw_parts(
222-
&dir.d_name as *const _ as *const u8,
223-
dir.d_reclen as usize - core::mem::size_of::<dirent64>() - 1,
224-
)
225-
.to_vec()
221+
CStr::from_ptr(&dir.d_name as *const _ as *const i8).to_bytes()
226222
};
227223
let entry = DirEntry {
228224
root: self.inner.root.clone(),
229225
ino: dir.d_ino,
230226
type_: dir.d_type as u32,
231-
name: OsString::from_vec(name_bytes),
227+
name: OsString::from_vec(name_bytes.to_vec()),
232228
};
233229

234230
return Some(Ok(entry));
@@ -237,7 +233,7 @@ impl Iterator for ReadDir {
237233
counter += 1;
238234

239235
// move to the next dirent64, which is directly stored after the previous one
240-
offset = offset + dir.d_off;
236+
offset = offset + usize::from(dir.d_reclen);
241237
}
242238
}
243239
}

0 commit comments

Comments
 (0)