Implement fd_filestat_get for all platforms (#42)

* Implement fd_filestat_get for all platforms

* Remove an old comment

* Remove panics from the syscall wrappers

* Return WASI error type

* Reuse Metadata if possible to save syscalls.

* Refactor the change for two separate fd_filestat_get_impl

* Refactor error handling
This commit is contained in:
Marcin Mielniczuk
2019-07-26 19:15:29 +02:00
committed by Jakub Konka
parent e759e3c2a4
commit 89fbde2c3f
7 changed files with 189 additions and 17 deletions

View File

@@ -1,9 +1,11 @@
#![allow(non_camel_case_types)]
use crate::{winerror, Result};
use std::ffi::{OsStr, OsString};
use std::os::windows::prelude::{OsStrExt, OsStringExt, RawHandle};
use std::ffi::{c_void, OsStr, OsString};
use std::fs::File;
use std::io;
use std::os::windows::prelude::{AsRawHandle, OsStrExt, OsStringExt, RawHandle};
use winapi::shared::minwindef::{self, DWORD};
use winapi::um::{fileapi, fileapi::GetFileType, winbase, winnt};
use winapi::um::{fileapi, fileapi::GetFileType, minwinbase, winbase, winnt};
/// Maximum total path length for Unicode in Windows.
/// [Maximum path length limitation]: https://docs.microsoft.com/en-us/windows/desktop/FileIO/naming-a-file#maximum-path-length-limitation
@@ -457,3 +459,48 @@ pub fn openat<S: AsRef<OsStr>>(
Ok(handle)
}
}
// Taken from Rust libstd, file libstd/sys/windows/fs.rs
fn cvt(i: winapi::shared::minwindef::BOOL) -> io::Result<()> {
if i == 0 {
Err(io::Error::last_os_error())
} else {
Ok(())
}
}
pub fn get_fileinfo(file: &File) -> io::Result<fileapi::BY_HANDLE_FILE_INFORMATION> {
use fileapi::{GetFileInformationByHandle, BY_HANDLE_FILE_INFORMATION};
use std::mem;
let handle = file.as_raw_handle();
let info = unsafe {
let mut info: BY_HANDLE_FILE_INFORMATION = mem::zeroed();
cvt(GetFileInformationByHandle(handle, &mut info))?;
info
};
Ok(info)
}
pub fn change_time(file: &File) -> io::Result<i64> {
use fileapi::FILE_BASIC_INFO;
use minwinbase::FileBasicInfo;
use std::mem;
use winbase::GetFileInformationByHandleEx;
let handle = file.as_raw_handle();
let tm = unsafe {
let mut info: FILE_BASIC_INFO = mem::zeroed();
let infosize = mem::size_of_val(&info);
cvt(GetFileInformationByHandleEx(
handle,
FileBasicInfo,
&mut info as *mut FILE_BASIC_INFO as *mut c_void,
infosize as u32,
))?;
*info.ChangeTime.QuadPart()
};
Ok(tm)
}