mirror of
https://github.com/fluencelabs/wasmer
synced 2025-03-16 16:20:49 +00:00
implement path_filestat_get
This commit is contained in:
parent
b80dd072a1
commit
7d728fc4cc
@ -8,7 +8,7 @@ pub mod windows;
|
||||
use self::types::*;
|
||||
use crate::{
|
||||
ptr::{Array, WasmPtr},
|
||||
state::{Kind, WasiState},
|
||||
state::{Kind, WasiState, MAX_SYMLINKS},
|
||||
};
|
||||
use rand::{thread_rng, Rng};
|
||||
use std::cell::Cell;
|
||||
@ -943,9 +943,9 @@ pub fn path_create_directory(
|
||||
/// Access metadata about a file or directory
|
||||
/// Inputs:
|
||||
/// - `__wasi_fd_t fd`
|
||||
/// The file to acces
|
||||
/// The directory that `path` is relative to
|
||||
/// - `__wasi_lookupflags_t flags`
|
||||
/// Flags to control how the path is understood
|
||||
/// Flags to control how `path` is understood
|
||||
/// - `const char *path`
|
||||
/// String containing the file path
|
||||
/// - `u32 path_len`
|
||||
@ -962,11 +962,57 @@ pub fn path_filestat_get(
|
||||
buf: WasmPtr<__wasi_filestat_t>,
|
||||
) -> __wasi_errno_t {
|
||||
debug!("wasi::path_filestat_get");
|
||||
let mut state = get_wasi_state(ctx);
|
||||
let state = get_wasi_state(ctx);
|
||||
let memory = ctx.memory(0);
|
||||
|
||||
// check __WASI_RIGHT_PATH_FILESTAT_GET
|
||||
unimplemented!()
|
||||
let root_dir = wasi_try!(state.fs.fd_map.get(&fd).ok_or(__WASI_EBADF));
|
||||
|
||||
if !has_rights(root_dir.rights, __WASI_RIGHT_PATH_FILESTAT_GET) {
|
||||
return __WASI_EACCES;
|
||||
}
|
||||
|
||||
let path_vec = wasi_try!(::std::str::from_utf8(unsafe {
|
||||
&*(wasi_try!(path.deref(memory, 0, path_len)) as *const [_] as *const [u8])
|
||||
})
|
||||
.map_err(|_| __WASI_EINVAL))
|
||||
.split('/')
|
||||
.map(|str| str.to_string())
|
||||
.collect::<Vec<String>>();
|
||||
let buf_cell = wasi_try!(buf.deref(memory));
|
||||
|
||||
// find the inode by traversing the path
|
||||
let mut inode = root_dir.inode;
|
||||
'outer: for segment in path_vec {
|
||||
// loop to traverse symlinks
|
||||
// TODO: proper cycle detection
|
||||
let mut sym_count = 0;
|
||||
loop {
|
||||
match &state.fs.inodes[inode].kind {
|
||||
Kind::Dir { entries, .. } => {
|
||||
if let Some(entry) = entries.get(&segment) {
|
||||
inode = entry.clone();
|
||||
continue 'outer;
|
||||
} else {
|
||||
return __WASI_ENOENT;
|
||||
}
|
||||
}
|
||||
Kind::Symlink { forwarded } => {
|
||||
sym_count += 1;
|
||||
inode = forwarded.clone();
|
||||
if sym_count > MAX_SYMLINKS {
|
||||
return __WASI_ELOOP;
|
||||
}
|
||||
}
|
||||
_ => return __WASI_ENOTDIR,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let stat = state.fs.inodes[inode].stat;
|
||||
|
||||
buf_cell.set(stat);
|
||||
|
||||
__WASI_ESUCCESS
|
||||
}
|
||||
|
||||
/// ### `path_filestat_set_times()`
|
||||
|
Loading…
x
Reference in New Issue
Block a user