From ee10a2b315f7dd883547261ffb551ad408454c42 Mon Sep 17 00:00:00 2001 From: YdrMaster Date: Sat, 26 Mar 2022 18:20:55 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E5=8E=BB=E9=99=A4=E8=AE=B8=E5=A4=9A?= =?UTF-8?q?=E8=AD=A6=E5=91=8A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit refactor: 将分散各处的声明初始化内存封装为一个 unsafe 函数,方便管理 feat(rcore-fs-hostfs): 实现设置宿主文件系统上文件最后访问时间和最后修改时间 --- rcore-fs-devfs/src/special/null.rs | 6 +++ rcore-fs-devfs/src/special/zero.rs | 6 +++ rcore-fs-ext2/src/lib.rs | 18 ++++---- rcore-fs-fuse/src/zip.rs | 12 ++--- rcore-fs-hostfs/src/lib.rs | 72 ++++++++++++++++++------------ rcore-fs-ramfs/src/lib.rs | 2 +- rcore-fs-sefs/src/lib.rs | 38 ++++++++-------- rcore-fs-sfs/src/lib.rs | 47 ++++++++++--------- rcore-fs-sfs/src/tests.rs | 31 ++++++------- rcore-fs/src/dev/block_cache.rs | 12 +++-- rcore-fs/src/dev/mod.rs | 13 +++--- rcore-fs/src/dirty.rs | 1 - rcore-fs/src/util.rs | 16 +++++++ 13 files changed, 157 insertions(+), 117 deletions(-) diff --git a/rcore-fs-devfs/src/special/null.rs b/rcore-fs-devfs/src/special/null.rs index 945d8f01..ab8dea35 100644 --- a/rcore-fs-devfs/src/special/null.rs +++ b/rcore-fs-devfs/src/special/null.rs @@ -12,6 +12,12 @@ impl NullINode { } } +impl Default for NullINode { + fn default() -> Self { + Self::new() + } +} + impl INode for NullINode { fn read_at(&self, _offset: usize, _buf: &mut [u8]) -> Result { // read nothing diff --git a/rcore-fs-devfs/src/special/zero.rs b/rcore-fs-devfs/src/special/zero.rs index 773a222d..f99e04f9 100644 --- a/rcore-fs-devfs/src/special/zero.rs +++ b/rcore-fs-devfs/src/special/zero.rs @@ -12,6 +12,12 @@ impl ZeroINode { } } +impl Default for ZeroINode { + fn default() -> Self { + Self::new() + } +} + impl INode for ZeroINode { fn read_at(&self, _offset: usize, buf: &mut [u8]) -> Result { // read zeros diff --git a/rcore-fs-ext2/src/lib.rs b/rcore-fs-ext2/src/lib.rs index a2616368..afd2e20f 100644 --- a/rcore-fs-ext2/src/lib.rs +++ b/rcore-fs-ext2/src/lib.rs @@ -38,10 +38,8 @@ struct Ext2Error { } impl core::convert::From for vfs::FsError { - fn from(err: Ext2Error) -> Self { - match err.inner { - _ => vfs::FsError::DeviceError, - } + fn from(_err: Ext2Error) -> Self { + vfs::FsError::DeviceError } } @@ -91,10 +89,10 @@ impl Volume for Ext2Volume { unimplemented!() } - unsafe fn slice_unchecked<'a>( - &'a self, + unsafe fn slice_unchecked( + &self, range: Range>, - ) -> VolumeSlice<'a, u8, Size512> { + ) -> VolumeSlice<'_, u8, Size512> { let index = range.start; let len = range.end - range.start; let mut vec = vec![0; len.into_index() as usize]; @@ -104,10 +102,10 @@ impl Volume for Ext2Volume { VolumeSlice::new_owned(vec, index) } - fn slice<'a>( - &'a self, + fn slice( + &self, range: Range>, - ) -> Result, Self::Error> { + ) -> Result, Self::Error> { let index = range.start; let len = range.end - range.start; let mut vec = vec![0; len.into_index() as usize]; diff --git a/rcore-fs-fuse/src/zip.rs b/rcore-fs-fuse/src/zip.rs index a70961d0..34111ad4 100644 --- a/rcore-fs-fuse/src/zip.rs +++ b/rcore-fs-fuse/src/zip.rs @@ -1,14 +1,16 @@ use std::error::Error; use std::fs; use std::io::{Read, Write}; -use std::mem::MaybeUninit; #[cfg(unix)] use std::os::unix::ffi::OsStrExt; use std::path::Path; use std::str; use std::sync::Arc; -use rcore_fs::vfs::{FileType, INode}; +use rcore_fs::{ + util::uninit_memory, + vfs::{FileType, INode}, +}; const DEFAULT_MODE: u32 = 0o664; const BUF_SIZE: usize = 0x1000; @@ -24,7 +26,7 @@ pub fn zip_dir(path: &Path, inode: Arc) -> Result<(), Box> let inode = inode.create(name, FileType::File, DEFAULT_MODE)?; let mut file = fs::File::open(entry.path())?; inode.resize(file.metadata()?.len() as usize)?; - let mut buf: [u8; BUF_SIZE] = unsafe { MaybeUninit::uninit().assume_init() }; + let mut buf: [u8; BUF_SIZE] = unsafe { uninit_memory() }; let mut offset = 0usize; let mut len = BUF_SIZE; while len == BUF_SIZE { @@ -59,7 +61,7 @@ pub fn unzip_dir(path: &Path, inode: Arc) -> Result<(), Box { let mut file = fs::File::create(&path)?; - let mut buf: [u8; BUF_SIZE] = unsafe { MaybeUninit::uninit().assume_init() }; + let mut buf: [u8; BUF_SIZE] = unsafe { uninit_memory() }; let mut offset = 0usize; let mut len = BUF_SIZE; while len == BUF_SIZE { @@ -73,7 +75,7 @@ pub fn unzip_dir(path: &Path, inode: Arc) -> Result<(), Box { - let mut buf: [u8; BUF_SIZE] = unsafe { MaybeUninit::uninit().assume_init() }; + let mut buf: [u8; BUF_SIZE] = unsafe { uninit_memory() }; let len = inode.read_at(0, buf.as_mut())?; #[cfg(unix)] std::os::unix::fs::symlink(str::from_utf8(&buf[..len]).unwrap(), path)?; diff --git a/rcore-fs-hostfs/src/lib.rs b/rcore-fs-hostfs/src/lib.rs index bf85bb3c..82fa1518 100644 --- a/rcore-fs-hostfs/src/lib.rs +++ b/rcore-fs-hostfs/src/lib.rs @@ -102,29 +102,43 @@ impl INode for HNode { Ok(metadata.into()) } - fn set_metadata(&self, _metadata: &Metadata) -> Result<()> { - warn!("HostFS: set_metadata() is unimplemented"); - Ok(()) + fn set_metadata(&self, metadata: &Metadata) -> Result<()> { + // TODO 仅修改了文件的最后访问时间和最后修改时间 + use nix::{ + libc::{timespec, AT_FDCWD}, + sys::{ + stat::{utimensat, UtimensatFlags::FollowSymlink}, + time::TimeSpec, + }, + }; + utimensat( + Some(AT_FDCWD), + &self.path, + &TimeSpec::from_timespec(timespec { + tv_sec: metadata.atime.sec, + tv_nsec: metadata.atime.nsec as _, + }), + &TimeSpec::from_timespec(timespec { + tv_sec: metadata.mtime.sec, + tv_nsec: metadata.mtime.nsec as _, + }), + FollowSymlink, + ) + .map_err(|_| FsError::InvalidParam) } fn sync_all(&self) -> Result<()> { - let mut guard = self.open_file()?; - let file = guard.as_mut().unwrap(); - file.sync_all()?; + self.open_file()?.as_mut().unwrap().sync_all()?; Ok(()) } fn sync_data(&self) -> Result<()> { - let mut guard = self.open_file()?; - let file = guard.as_mut().unwrap(); - file.sync_data()?; + self.open_file()?.as_mut().unwrap().sync_data()?; Ok(()) } fn resize(&self, len: usize) -> Result<()> { - let mut guard = self.open_file()?; - let file = guard.as_mut().unwrap(); - file.set_len(len as u64)?; + self.open_file()?.as_mut().unwrap().set_len(len as u64)?; Ok(()) } @@ -177,27 +191,29 @@ impl INode for HNode { fn find(&self, name: &str) -> Result> { let new_path = self.path.join(name); - if !new_path.exists() { - return Err(FsError::EntryNotFound); + if new_path.exists() { + Ok(Arc::new(HNode { + path: new_path, + file: Mutex::new(None), + fs: self.fs.clone(), + })) + } else { + Err(FsError::EntryNotFound) } - Ok(Arc::new(HNode { - path: new_path, - file: Mutex::new(None), - fs: self.fs.clone(), - })) } fn get_entry(&self, id: usize) -> Result { - if !self.path.is_dir() { - return Err(FsError::NotDir); + if self.path.is_dir() { + self.path + .read_dir()? + .nth(id) + .ok_or(FsError::EntryNotFound)?? + .file_name() + .into_string() + .map_err(|_| FsError::InvalidParam) + } else { + Err(FsError::NotDir) } - self.path - .read_dir()? - .nth(id) - .ok_or(FsError::EntryNotFound)?? - .file_name() - .into_string() - .map_err(|_| FsError::InvalidParam) } fn io_control(&self, _cmd: u32, _data: usize) -> Result { diff --git a/rcore-fs-ramfs/src/lib.rs b/rcore-fs-ramfs/src/lib.rs index b56c3269..731391f4 100644 --- a/rcore-fs-ramfs/src/lib.rs +++ b/rcore-fs-ramfs/src/lib.rs @@ -251,7 +251,7 @@ impl INode for LockedINode { return Err(FsError::DirNotEmpty); } let other = file.children.get(name).ok_or(FsError::EntryNotFound)?; - if other.0.read().children.len() > 0 { + if !other.0.read().children.is_empty() { return Err(FsError::DirNotEmpty); } other.0.write().extra.nlinks -= 1; diff --git a/rcore-fs-sefs/src/lib.rs b/rcore-fs-sefs/src/lib.rs index ee8b0fea..3d91f873 100644 --- a/rcore-fs-sefs/src/lib.rs +++ b/rcore-fs-sefs/src/lib.rs @@ -11,16 +11,18 @@ use alloc::{ }; use core::any::Any; use core::fmt::{Debug, Error, Formatter}; -use core::mem::MaybeUninit; use bitvec::prelude::*; -use rcore_fs::dev::TimeProvider; -use rcore_fs::dirty::Dirty; -use rcore_fs::vfs::{self, FileSystem, FsError, INode, MMapArea, Timespec}; +use rcore_fs::{ + dev::TimeProvider, + dirty::Dirty, + util::uninit_memory, + vfs::{self, FileSystem, FsError, INode, MMapArea, Timespec}, +}; use spin::RwLock; -use self::dev::*; -use self::structs::*; +use dev::*; +use structs::*; pub mod dev; mod structs; @@ -36,7 +38,7 @@ impl dyn File { self.write_all_at(buf, id * BLKSIZE) } fn read_direntry(&self, id: usize) -> DevResult { - let mut direntry: DiskEntry = unsafe { MaybeUninit::uninit().assume_init() }; + let mut direntry: DiskEntry = unsafe { uninit_memory() }; self.read_exact_at(direntry.as_buf_mut(), DIRENT_SIZE * id)?; Ok(direntry) } @@ -45,7 +47,7 @@ impl dyn File { } /// Load struct `T` from given block in device fn load_struct(&self, id: BlockId) -> DevResult { - let mut s: T = unsafe { MaybeUninit::uninit().assume_init() }; + let mut s: T = unsafe { uninit_memory() }; self.read_block(id, s.as_buf_mut())?; Ok(s) } @@ -179,7 +181,7 @@ impl vfs::INode for INodeImpl { _ => panic!("Unknown file type"), }, mode: disk_inode.mode, - type_: vfs::FileType::from(disk_inode.type_.clone()), + type_: vfs::FileType::from(disk_inode.type_), blocks: disk_inode.blocks as usize, atime: Timespec { sec: disk_inode.atime as i64, @@ -250,12 +252,12 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } // Ensure the name is not exist - if !self.get_file_inode_id(name).is_none() { + if self.get_file_inode_id(name).is_some() { return Err(FsError::EntryExist); } @@ -284,7 +286,7 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } if name == "." { @@ -321,10 +323,10 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } - if !self.get_file_inode_id(name).is_none() { + if self.get_file_inode_id(name).is_some() { return Err(FsError::EntryExist); } let child = other @@ -349,7 +351,7 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } if old_name == "." { @@ -369,7 +371,7 @@ impl vfs::INode for INodeImpl { if dest_info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if dest_info.nlinks <= 0 { + if dest_info.nlinks == 0 { return Err(FsError::DirRemoved); } if dest.get_file_inode_id(new_name).is_some() { @@ -442,7 +444,7 @@ impl Drop for INodeImpl { fn drop(&mut self) { self.sync_all() .expect("Failed to sync when dropping the SEFS Inode"); - if self.disk_inode.read().nlinks <= 0 { + if self.disk_inode.read().nlinks == 0 { self.disk_inode.write().sync(); self.fs.free_block(self.id); self.fs.device.remove(self.id).unwrap(); @@ -654,7 +656,7 @@ impl SEFS { .map(|(&id, _)| id) .collect(); for id in remove_ids.iter() { - inodes.remove(&id); + inodes.remove(id); } } fn get_freemap_block_id_of_group(group_id: usize) -> usize { diff --git a/rcore-fs-sfs/src/lib.rs b/rcore-fs-sfs/src/lib.rs index d03c88d0..1612102b 100644 --- a/rcore-fs-sfs/src/lib.rs +++ b/rcore-fs-sfs/src/lib.rs @@ -11,19 +11,22 @@ use alloc::{ vec, vec::Vec, }; -use core::any::Any; -use core::fmt::{Debug, Error, Formatter}; -use core::mem::MaybeUninit; +use core::{ + any::Any, + fmt::{Debug, Error, Formatter}, +}; use bitvec::prelude::*; use spin::RwLock; -use rcore_fs::dev::Device; -use rcore_fs::dirty::Dirty; -use rcore_fs::util::*; -use rcore_fs::vfs::{self, FileSystem, FsError, INode, MMapArea, Metadata}; +use rcore_fs::{ + dev::Device, + dirty::Dirty, + util::*, + vfs::{self, FileSystem, FsError, INode, MMapArea, Metadata}, +}; -pub use self::structs::*; +pub use structs::*; mod structs; #[cfg(test)] @@ -46,7 +49,7 @@ trait DeviceExt: Device { } /// Load struct `T` from given block in device fn load_struct(&self, id: BlockId) -> vfs::Result { - let mut s: T = unsafe { MaybeUninit::uninit().assume_init() }; + let mut s: T = unsafe { uninit_memory() }; self.read_block(id, 0, s.as_buf_mut())?; Ok(s) } @@ -185,7 +188,7 @@ impl INodeImpl { Ok(()) } fn read_direntry(&self, id: usize) -> vfs::Result { - let mut direntry: DiskEntry = unsafe { MaybeUninit::uninit().assume_init() }; + let mut direntry: DiskEntry = unsafe { uninit_memory() }; self._read_at(DIRENT_SIZE * id, direntry.as_buf_mut())?; Ok(direntry) } @@ -374,10 +377,10 @@ impl INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } - if !self.get_file_inode_id(name).is_none() { + if self.get_file_inode_id(name).is_some() { return Err(FsError::EntryExist); } let child = other; @@ -458,7 +461,7 @@ impl vfs::INode for INodeImpl { _ => panic!("Unknown file type"), }, mode: 0o777, - type_: vfs::FileType::from(disk_inode.type_.clone()), + type_: vfs::FileType::from(disk_inode.type_), blocks: disk_inode.blocks as usize, atime: disk_inode.atime, mtime: disk_inode.mtime, @@ -509,12 +512,12 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } // Ensure the name is not exist - if !self.get_file_inode_id(name).is_none() { + if self.get_file_inode_id(name).is_some() { return Err(FsError::EntryExist); } @@ -546,10 +549,10 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } - if !self.get_file_inode_id(name).is_none() { + if self.get_file_inode_id(name).is_some() { return Err(FsError::EntryExist); } let child = other @@ -573,7 +576,7 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } if name == "." { @@ -609,7 +612,7 @@ impl vfs::INode for INodeImpl { if info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if info.nlinks <= 0 { + if info.nlinks == 0 { return Err(FsError::DirRemoved); } if old_name == "." { @@ -629,7 +632,7 @@ impl vfs::INode for INodeImpl { if dest_info.type_ != vfs::FileType::Dir { return Err(FsError::NotDir); } - if dest_info.nlinks <= 0 { + if dest_info.nlinks == 0 { return Err(FsError::DirRemoved); } if let Some((_, id)) = dest.get_file_inode_and_entry_id(new_name) { @@ -727,7 +730,7 @@ impl Drop for INodeImpl { fn drop(&mut self) { self.sync_all() .expect("Failed to sync when dropping the SimpleFileSystem Inode"); - if self.disk_inode.read().nlinks <= 0 { + if self.disk_inode.read().nlinks == 0 { self._resize(0).unwrap(); self.disk_inode.write().sync(); self.fs.free_block(self.id); @@ -934,7 +937,7 @@ impl SimpleFileSystem { .map(|(&id, _)| id) .collect(); for id in remove_ids.iter() { - inodes.remove(&id); + inodes.remove(id); } } } diff --git a/rcore-fs-sfs/src/tests.rs b/rcore-fs-sfs/src/tests.rs index 6de0b933..2f0ddb7b 100644 --- a/rcore-fs-sfs/src/tests.rs +++ b/rcore-fs-sfs/src/tests.rs @@ -1,11 +1,14 @@ extern crate std; use crate::*; -use rcore_fs::vfs::{FileSystem, FileType, Metadata, Result, Timespec}; -use std::fs::{self, OpenOptions}; - -use std::sync::Arc; -use std::sync::Mutex; +use rcore_fs::{ + util::uninit_memory, + vfs::{FileSystem, FileType, Metadata, Result, Timespec}, +}; +use std::{ + fs::{self, OpenOptions}, + sync::{Arc, Mutex}, +}; fn _open_sample_file() -> Arc { fs::copy("sfs.img", "test.img").expect("failed to open sfs.img"); @@ -76,7 +79,7 @@ fn resize() -> Result<()> { const SIZE2: usize = 0x1250; file1.resize(SIZE1)?; assert_eq!(file1.metadata()?.size, SIZE1, "wrong size after resize"); - let mut data1: [u8; SIZE2] = unsafe { MaybeUninit::uninit().assume_init() }; + let mut data1: [u8; SIZE2] = unsafe { uninit_memory() }; let len = file1.read_at(0, data1.as_mut())?; assert_eq!(len, SIZE1, "wrong size returned by read_at()"); assert_eq!( @@ -540,26 +543,20 @@ fn create_then_get_entry() -> Result<()> { let sfs = _create_new_sfs(); let root = sfs.root_inode(); + assert!(root.get_entry(0).unwrap() == *".", "entry 0 is ."); assert!( - root.get_entry(0).unwrap() == String::from("."), - "entry 0 is ." - ); - assert!( - root.get_entry_with_metadata(0).unwrap().1 == String::from("."), + root.get_entry_with_metadata(0).unwrap().1 == *".", "entry 0 is ." ); + assert!(root.get_entry(1).unwrap() == *"..", "entry 1 is .."); assert!( - root.get_entry(1).unwrap() == String::from(".."), - "entry 1 is .." - ); - assert!( - root.get_entry_with_metadata(1).unwrap().1 == String::from(".."), + root.get_entry_with_metadata(1).unwrap().1 == *"..", "entry 1 is .." ); let _file1 = root.create("file1", FileType::File, 0o777)?; assert!( - root.get_entry_with_metadata(2).unwrap().1 == String::from("file1"), + root.get_entry_with_metadata(2).unwrap().1 == *"file1", "entry 2 is file1" ); diff --git a/rcore-fs/src/dev/block_cache.rs b/rcore-fs/src/dev/block_cache.rs index 881a2b1a..0d705f81 100644 --- a/rcore-fs/src/dev/block_cache.rs +++ b/rcore-fs/src/dev/block_cache.rs @@ -93,13 +93,10 @@ impl BlockDevice for BlockCache { fn read_at(&self, block_id: BlockId, buffer: &mut [u8]) -> Result<()> { let mut buf = self.get_buf(block_id); - match buf.status { - BufStatus::Unused => { - // read from device - self.device.read_at(block_id, &mut buf.data)?; - buf.status = BufStatus::Valid(block_id); - } - _ => {} + if let BufStatus::Unused = buf.status { + // read from device + self.device.read_at(block_id, &mut buf.data)?; + buf.status = BufStatus::Valid(block_id); } let len = 1 << Self::BLOCK_SIZE_LOG2 as usize; buffer[..len].copy_from_slice(&buf.data); @@ -124,6 +121,7 @@ impl BlockDevice for BlockCache { } /// Doubly circular linked list LRU manager +#[allow(clippy::upper_case_acronyms)] struct LRU { prev: Vec, next: Vec, diff --git a/rcore-fs/src/dev/mod.rs b/rcore-fs/src/dev/mod.rs index f0b09093..ffb19b20 100644 --- a/rcore-fs/src/dev/mod.rs +++ b/rcore-fs/src/dev/mod.rs @@ -1,5 +1,4 @@ -use crate::util::*; -use crate::vfs::Timespec; +use crate::{util::*, vfs::Timespec}; pub mod block_cache; pub mod std_impl; @@ -58,13 +57,12 @@ impl Device for T { // Read to target buf directly try0!(len, BlockDevice::read_at(self, range.block, buf)); } else { - use core::mem::MaybeUninit; - let mut block_buf: [u8; 1 << 10] = unsafe { MaybeUninit::uninit().assume_init() }; + let mut block_buf: [u8; 1 << 10] = unsafe { uninit_memory() }; assert!(Self::BLOCK_SIZE_LOG2 <= 10); // Read to local buf first try0!(len, BlockDevice::read_at(self, range.block, &mut block_buf)); // Copy to target buf then - buf.copy_from_slice(&mut block_buf[range.begin..range.end]); + buf.copy_from_slice(&block_buf[range.begin..range.end]); } } Ok(buf.len()) @@ -85,8 +83,7 @@ impl Device for T { // Write to target buf directly try0!(len, BlockDevice::write_at(self, range.block, buf)); } else { - use core::mem::MaybeUninit; - let mut block_buf: [u8; 1 << 10] = unsafe { MaybeUninit::uninit().assume_init() }; + let mut block_buf: [u8; 1 << 10] = unsafe { uninit_memory() }; assert!(Self::BLOCK_SIZE_LOG2 <= 10); // Read to local buf first try0!(len, BlockDevice::read_at(self, range.block, &mut block_buf)); @@ -116,7 +113,7 @@ mod test { return Err(DevError); } let begin = block_id << 2; - buf[..4].copy_from_slice(&mut self.lock().unwrap()[begin..begin + 4]); + buf[..4].copy_from_slice(&self.lock().unwrap()[begin..begin + 4]); Ok(()) } fn write_at(&self, block_id: BlockId, buf: &[u8]) -> Result<()> { diff --git a/rcore-fs/src/dirty.rs b/rcore-fs/src/dirty.rs index a997c872..b99148fc 100644 --- a/rcore-fs/src/dirty.rs +++ b/rcore-fs/src/dirty.rs @@ -26,7 +26,6 @@ impl Dirty { } /// Returns true if dirty, false otherwise - #[allow(dead_code)] pub fn dirty(&self) -> bool { self.dirty } diff --git a/rcore-fs/src/util.rs b/rcore-fs/src/util.rs index a72ed98d..af56da39 100644 --- a/rcore-fs/src/util.rs +++ b/rcore-fs/src/util.rs @@ -14,6 +14,9 @@ pub struct BlockRange { } impl BlockRange { + pub fn is_empty(&self) -> bool { + self.end == self.begin + } pub fn len(&self) -> usize { self.end - self.begin } @@ -54,6 +57,19 @@ impl Iterator for BlockIter { } } +// 声明一块未初始化的内存 +/// Declares a block of uninitialized memory. +/// +/// # Safety +/// +/// Never read from uninitialized memory! +#[inline(always)] +pub unsafe fn uninit_memory() -> T { + // 这个写法十分恐怖,但实际上是死灵书的正牌写法 + #[allow(clippy::uninit_assumed_init)] + core::mem::MaybeUninit::uninit().assume_init() +} + #[cfg(test)] mod test { use super::*;