diff --git a/src/kernel/src/fs/host/file.rs b/src/kernel/src/fs/host/file.rs index aa75d284e..70c64d4f9 100644 --- a/src/kernel/src/fs/host/file.rs +++ b/src/kernel/src/fs/host/file.rs @@ -197,27 +197,27 @@ impl HostFile { Err(Error::last_os_error()) } else { // TODO: Store mode somewhere that work on any FS. We should not use mode on the host - // for this because it can be lose when the user restore their files from the backup. + // for this because it can be lost when the user restores their files from the backup. Self::raw_open(parent, name) } } #[cfg(windows)] - fn raw_mkdir(parent: RawFile, name: &str, mode: u32) -> Result { + fn raw_mkdir(parent: RawFile, name: &str, _mode: u32) -> Result { use std::mem::size_of; use std::ptr::null_mut; - use windows_sys::Wdk::Foundation::OBJECT_ATTRIBUTES; - use windows_sys::Wdk::Storage::FileSystem::{ - NtCreateFile, FILE_CREATE, FILE_DIRECTORY_FILE, + use windows_sys::Wdk::{ + Foundation::OBJECT_ATTRIBUTES, + Storage::FileSystem::{NtCreateFile, FILE_DIRECTORY_FILE, FILE_OPEN}, }; - use windows_sys::Win32::Foundation::{ - RtlNtStatusToDosError, STATUS_SUCCESS, UNICODE_STRING, - }; - use windows_sys::Win32::Storage::FileSystem::{ - FILE_ATTRIBUTE_DIRECTORY, FILE_LIST_DIRECTORY, FILE_READ_ATTRIBUTES, FILE_READ_EA, - FILE_SHARE_READ, FILE_SHARE_WRITE, FILE_TRAVERSE, FILE_WRITE_ATTRIBUTES, FILE_WRITE_EA, + use windows_sys::Win32::{ + Foundation::{RtlNtStatusToDosError, STATUS_SUCCESS, UNICODE_STRING}, + Storage::FileSystem::{ + FILE_ATTRIBUTE_DIRECTORY, FILE_LIST_DIRECTORY, FILE_READ_ATTRIBUTES, FILE_READ_EA, + FILE_SHARE_READ, FILE_SHARE_WRITE, FILE_TRAVERSE, FILE_WRITE_ATTRIBUTES, + FILE_WRITE_EA, + }, }; - use windows_sys::Win32::System::WindowsProgramming::FILE_EXISTS; // Encode name. let mut name: Vec = name.encode_utf16().collect(); @@ -255,7 +255,7 @@ impl HostFile { null_mut(), FILE_ATTRIBUTE_DIRECTORY, FILE_SHARE_READ | FILE_SHARE_WRITE, - FILE_CREATE, + FILE_OPEN, FILE_DIRECTORY_FILE, null_mut(), 0, @@ -344,7 +344,8 @@ impl HostFile { use std::ptr::null_mut; use windows_sys::Wdk::Foundation::OBJECT_ATTRIBUTES; use windows_sys::Wdk::Storage::FileSystem::{ - NtCreateFile, FILE_NON_DIRECTORY_FILE, FILE_OPEN, FILE_RANDOM_ACCESS, + NtCreateFile, FILE_DIRECTORY_FILE, FILE_NON_DIRECTORY_FILE, FILE_OPEN, + FILE_RANDOM_ACCESS, }; use windows_sys::Win32::Foundation::{ RtlNtStatusToDosError, STATUS_SUCCESS, UNICODE_STRING, @@ -394,10 +395,30 @@ impl HostFile { if err == STATUS_SUCCESS { Ok(handle) } else { - // TODO: Check if file is a directory. - Err(Error::from_raw_os_error(unsafe { - RtlNtStatusToDosError(err).try_into().unwrap() - })) + // Try open as a directory. + let err = unsafe { + NtCreateFile( + &mut handle, + DELETE | FILE_GENERIC_READ | FILE_GENERIC_WRITE, + &mut attr, + &mut status, + null_mut(), + 0, + 0, + FILE_OPEN, + FILE_DIRECTORY_FILE, + null_mut(), + 0, + ) + }; + + if err == STATUS_SUCCESS { + Ok(handle) + } else { + Err(Error::from_raw_os_error(unsafe { + RtlNtStatusToDosError(err).try_into().unwrap() + })) + } } } } diff --git a/src/kernel/src/fs/host/vnode.rs b/src/kernel/src/fs/host/vnode.rs index ee47d2323..df901e86e 100644 --- a/src/kernel/src/fs/host/vnode.rs +++ b/src/kernel/src/fs/host/vnode.rs @@ -87,8 +87,10 @@ impl crate::fs::VnodeBackend for VnodeBackend { return Err(Box::new(LookupError::InvalidName)); } + let host_file = self.file.open(name).map_err(LookupError::OpenFailed)?; + // Lookup the file. - Cow::Owned(self.file.open(name).map_err(LookupError::OpenFailed)?) + Cow::Owned(host_file) } }; diff --git a/src/kernel/src/fs/null/mod.rs b/src/kernel/src/fs/null/mod.rs index f555adab3..3b5427a2e 100644 --- a/src/kernel/src/fs/null/mod.rs +++ b/src/kernel/src/fs/null/mod.rs @@ -3,7 +3,7 @@ use super::{ Filesystem, Fs, FsConfig, LookupError, Mount, MountFlags, MountOpts, MountSource, VPathBuf, Vnode, }; -use crate::errno::{Errno, EDEADLK, EOPNOTSUPP}; +use crate::errno::{Errno, EOPNOTSUPP}; use crate::ucred::Ucred; use macros::Errno; use std::sync::Arc; diff --git a/src/kernel/src/time/mod.rs b/src/kernel/src/time/mod.rs index cb79ffb88..6dade86d7 100644 --- a/src/kernel/src/time/mod.rs +++ b/src/kernel/src/time/mod.rs @@ -66,8 +66,8 @@ impl From for TimeSpec { #[repr(C)] struct TimeVal { - sec: i64, // tv_sec - usec: i64, // tv_usec + sec: i64, // tv_sec (seconds) + usec: i64, // tv_usec (microseconds) } impl TimeVal { @@ -88,37 +88,24 @@ impl TimeVal { #[cfg(windows)] fn microtime() -> Result { use std::mem::MaybeUninit; - use windows_sys::Win32::System::{ - SystemInformation::GetSystemTime, Time::SystemTimeToFileTime, - }; + use windows_sys::Win32::System::SystemInformation::GetSystemTimePreciseAsFileTime; - // The number of hundreds of nanoseconds between the Windows epoch (1601-01-01T00:00:00Z) - // and the Unix epoch (1970-01-01T00:00:00Z) - const EPOCH: u64 = 116444736000000000; + let mut file_time = MaybeUninit::uninit(); - let mut system_time = MaybeUninit::uninit(); - let mut filetime = MaybeUninit::uninit(); - - let (system_time, filetime) = unsafe { - GetSystemTime(system_time.as_mut_ptr()); - let res = SystemTimeToFileTime(system_time.as_ptr(), filetime.as_mut_ptr()); - - if res == 0 { - Err(std::io::Error::last_os_error())? - } + unsafe { + GetSystemTimePreciseAsFileTime(file_time.as_mut_ptr()); + } - (system_time.assume_init(), filetime.assume_init()) - }; + let file_time = unsafe { file_time.assume_init() }; - let mut time = 0; + let intervals = (file_time.dwHighDateTime as u64) << 32 | file_time.dwLowDateTime as u64; - time += filetime.dwLowDateTime as u64; - time += (filetime.dwHighDateTime as u64) << 32; + let sec = (intervals / 10_000_000 - 11_644_473_600) + .try_into() + .unwrap(); + let usec = (intervals % 10_000_000).try_into().unwrap(); - Ok(Self { - sec: ((time - EPOCH) / 10_000_000) as i64, - usec: (system_time.wMilliseconds * 1000) as i64, - }) + Ok(Self { sec, usec }) } }