Skip to content

Commit 82df0a1

Browse files
fix: mkdir输出错误信息; feat: 实现get_pathname (#615)
* fix: mkdir输出错误信息; feat: 实现get_pathname * fix: 将处理路径的操作放入vfs而不是在syscall/mod.rs中 * 调整入参类型 --------- Co-authored-by: longjin <[email protected]>
1 parent 9e481b3 commit 82df0a1

File tree

5 files changed

+114
-259
lines changed

5 files changed

+114
-259
lines changed

kernel/src/filesystem/vfs/core.rs

Lines changed: 6 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,7 @@ use alloc::{format, string::ToString, sync::Arc};
44
use system_error::SystemError;
55

66
use crate::{
7-
driver::{
8-
base::block::disk_info::Partition,
9-
disk::ahci::{self},
10-
},
7+
driver::{base::block::disk_info::Partition, disk::ahci},
118
filesystem::{
129
devfs::devfs_init,
1310
fat::fs::FATFileSystem,
@@ -23,7 +20,7 @@ use crate::{
2320
use super::{
2421
file::FileMode,
2522
utils::{rsplit_path, user_path_at},
26-
IndexNode, InodeId, MAX_PATHLEN, VFS_MAX_FOLLOW_SYMLINK_TIMES,
23+
IndexNode, InodeId, VFS_MAX_FOLLOW_SYMLINK_TIMES,
2724
};
2825

2926
/// @brief 原子地生成新的Inode号。
@@ -181,10 +178,7 @@ pub fn mount_root_fs() -> Result<(), SystemError> {
181178

182179
/// @brief 创建文件/文件夹
183180
pub fn do_mkdir(path: &str, _mode: FileMode) -> Result<u64, SystemError> {
184-
// 文件名过长
185-
if path.len() > MAX_PATHLEN as usize {
186-
return Err(SystemError::ENAMETOOLONG);
187-
}
181+
let path = path.trim();
188182

189183
let inode: Result<Arc<dyn IndexNode>, SystemError> = ROOT_INODE().lookup(path);
190184

@@ -213,10 +207,7 @@ pub fn do_mkdir(path: &str, _mode: FileMode) -> Result<u64, SystemError> {
213207

214208
/// @brief 删除文件夹
215209
pub fn do_remove_dir(dirfd: i32, path: &str) -> Result<u64, SystemError> {
216-
// 文件名过长
217-
if path.len() > MAX_PATHLEN as usize {
218-
return Err(SystemError::ENAMETOOLONG);
219-
}
210+
let path = path.trim();
220211

221212
let pcb = ProcessManager::current_pcb();
222213
let (inode_begin, remain_path) = user_path_at(&pcb, dirfd, path)?;
@@ -249,10 +240,8 @@ pub fn do_remove_dir(dirfd: i32, path: &str) -> Result<u64, SystemError> {
249240

250241
/// @brief 删除文件
251242
pub fn do_unlink_at(dirfd: i32, path: &str) -> Result<u64, SystemError> {
252-
// 文件名过长
253-
if path.len() > MAX_PATHLEN as usize {
254-
return Err(SystemError::ENAMETOOLONG);
255-
}
243+
let path = path.trim();
244+
256245
let pcb = ProcessManager::current_pcb();
257246
let (inode_begin, remain_path) = user_path_at(&pcb, dirfd, path)?;
258247
let inode: Result<Arc<dyn IndexNode>, SystemError> =

kernel/src/filesystem/vfs/open.rs

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -36,10 +36,6 @@ pub(super) fn do_faccessat(
3636

3737
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
3838

39-
if path.len() == 0 {
40-
return Err(SystemError::EINVAL);
41-
}
42-
4339
let (inode, path) = user_path_at(&ProcessManager::current_pcb(), dirfd, &path)?;
4440

4541
// 如果找不到文件,则返回错误码ENOENT
@@ -52,10 +48,6 @@ pub(super) fn do_faccessat(
5248
pub fn do_fchmodat(dirfd: i32, path: *const u8, _mode: ModeType) -> Result<usize, SystemError> {
5349
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
5450

55-
if path.len() == 0 {
56-
return Err(SystemError::EINVAL);
57-
}
58-
5951
let (inode, path) = user_path_at(&ProcessManager::current_pcb(), dirfd, &path)?;
6052

6153
// 如果找不到文件,则返回错误码ENOENT
@@ -85,10 +77,8 @@ fn do_sys_openat2(
8577
follow_symlink: bool,
8678
) -> Result<usize, SystemError> {
8779
// kdebug!("open: path: {}, mode: {:?}", path, mode);
88-
// 文件名过长
89-
if path.len() > MAX_PATHLEN as usize {
90-
return Err(SystemError::ENAMETOOLONG);
91-
}
80+
let path = path.trim();
81+
9282
let (inode_begin, path) = user_path_at(&ProcessManager::current_pcb(), dirfd, path)?;
9383
let inode: Result<Arc<dyn IndexNode>, SystemError> = inode_begin.lookup_follow_symlink(
9484
&path,

kernel/src/filesystem/vfs/syscall.rs

Lines changed: 75 additions & 77 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,16 @@
1-
use core::ffi::CStr;
1+
use core::mem::size_of;
22

3-
use alloc::{
4-
string::{String, ToString},
5-
sync::Arc,
6-
vec::Vec,
7-
};
3+
use alloc::{string::String, sync::Arc, vec::Vec};
84
use system_error::SystemError;
95

106
use crate::{
117
driver::base::{block::SeekFrom, device::device_number::DeviceNumber},
128
filesystem::vfs::file::FileDescriptorVec,
13-
kerror,
149
libs::rwlock::RwLockWriteGuard,
1510
mm::{verify_area, VirtAddr},
1611
process::ProcessManager,
1712
syscall::{
18-
user_access::{check_and_clone_cstr, UserBufferReader, UserBufferWriter},
13+
user_access::{check_and_clone_cstr, UserBufferWriter},
1914
Syscall,
2015
},
2116
time::TimeSpec,
@@ -86,6 +81,7 @@ bitflags! {
8681
}
8782

8883
#[repr(C)]
84+
#[derive(Clone, Copy)]
8985
/// # 文件信息结构体
9086
pub struct PosixKstat {
9187
/// 硬件设备ID
@@ -248,22 +244,34 @@ impl Syscall {
248244
///
249245
/// @return 文件描述符编号,或者是错误码
250246
pub fn open(
251-
path: &str,
252-
flags: FileMode,
253-
mode: ModeType,
247+
path: *const u8,
248+
o_flags: u32,
249+
mode: u32,
254250
follow_symlink: bool,
255251
) -> Result<usize, SystemError> {
256-
return do_sys_open(AtFlags::AT_FDCWD.bits(), path, flags, mode, follow_symlink);
252+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
253+
let open_flags: FileMode = FileMode::from_bits(o_flags).ok_or(SystemError::EINVAL)?;
254+
let mode = ModeType::from_bits(mode as u32).ok_or(SystemError::EINVAL)?;
255+
return do_sys_open(
256+
AtFlags::AT_FDCWD.bits(),
257+
&path,
258+
open_flags,
259+
mode,
260+
follow_symlink,
261+
);
257262
}
258263

259264
pub fn openat(
260265
dirfd: i32,
261-
path: &str,
262-
o_flags: FileMode,
263-
mode: ModeType,
266+
path: *const u8,
267+
o_flags: u32,
268+
mode: u32,
264269
follow_symlink: bool,
265270
) -> Result<usize, SystemError> {
266-
return do_sys_open(dirfd, path, o_flags, mode, follow_symlink);
271+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
272+
let open_flags: FileMode = FileMode::from_bits(o_flags).ok_or(SystemError::EINVAL)?;
273+
let mode = ModeType::from_bits(mode as u32).ok_or(SystemError::EINVAL)?;
274+
return do_sys_open(dirfd, &path, open_flags, mode, follow_symlink);
267275
}
268276

269277
/// @brief 关闭文件
@@ -351,7 +359,15 @@ impl Syscall {
351359
///
352360
/// @return Ok(usize) 调整后,文件访问指针相对于文件头部的偏移量
353361
/// @return Err(SystemError) 调整失败,返回posix错误码
354-
pub fn lseek(fd: i32, seek: SeekFrom) -> Result<usize, SystemError> {
362+
pub fn lseek(fd: i32, offset: i64, seek: u32) -> Result<usize, SystemError> {
363+
let seek = match seek {
364+
SEEK_SET => Ok(SeekFrom::SeekSet(offset)),
365+
SEEK_CUR => Ok(SeekFrom::SeekCurrent(offset)),
366+
SEEK_END => Ok(SeekFrom::SeekEnd(offset)),
367+
SEEK_MAX => Ok(SeekFrom::SeekEnd(0)),
368+
_ => Err(SystemError::EINVAL),
369+
}?;
370+
355371
let binding = ProcessManager::current_pcb().fd_table();
356372
let fd_table_guard = binding.read();
357373
let file = fd_table_guard
@@ -429,10 +445,14 @@ impl Syscall {
429445
/// EFAULT | 错误的地址
430446
///
431447
/// ENAMETOOLONG | 路径过长
432-
pub fn chdir(dest_path: &str) -> Result<usize, SystemError> {
448+
pub fn chdir(path: *const u8) -> Result<usize, SystemError> {
449+
if path.is_null() {
450+
return Err(SystemError::EFAULT);
451+
}
452+
453+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
433454
let proc = ProcessManager::current_pcb();
434455
// Copy path to kernel space to avoid some security issues
435-
let path = dest_path.to_string();
436456
let mut new_path = String::from("");
437457
if path.len() > 0 {
438458
let cwd = match path.as_bytes()[0] {
@@ -461,8 +481,7 @@ impl Syscall {
461481
}
462482
let inode =
463483
match ROOT_INODE().lookup_follow_symlink(&new_path, VFS_MAX_FOLLOW_SYMLINK_TIMES) {
464-
Err(e) => {
465-
kerror!("Change Directory Failed, Error = {:?}", e);
484+
Err(_) => {
466485
return Err(SystemError::ENOENT);
467486
}
468487
Ok(i) => i,
@@ -534,8 +553,9 @@ impl Syscall {
534553
/// @param path(r8) 路径 / mode(r9) 模式
535554
///
536555
/// @return uint64_t 负数错误码 / 0表示成功
537-
pub fn mkdir(path: &str, mode: usize) -> Result<usize, SystemError> {
538-
return do_mkdir(path, FileMode::from_bits_truncate(mode as u32)).map(|x| x as usize);
556+
pub fn mkdir(path: *const u8, mode: usize) -> Result<usize, SystemError> {
557+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
558+
return do_mkdir(&path, FileMode::from_bits_truncate(mode as u32)).map(|x| x as usize);
539559
}
540560

541561
/// **删除文件夹、取消文件的链接、删除文件的系统调用**
@@ -547,14 +567,15 @@ impl Syscall {
547567
/// - `flags`:标志位
548568
///
549569
///
550-
pub fn unlinkat(dirfd: i32, pathname: &str, flags: u32) -> Result<usize, SystemError> {
570+
pub fn unlinkat(dirfd: i32, path: *const u8, flags: u32) -> Result<usize, SystemError> {
551571
let flags = AtFlags::from_bits(flags as i32).ok_or(SystemError::EINVAL)?;
552572

573+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
574+
553575
if flags.contains(AtFlags::AT_REMOVEDIR) {
554576
// kdebug!("rmdir");
555-
match do_remove_dir(dirfd, &pathname) {
577+
match do_remove_dir(dirfd, &path) {
556578
Err(err) => {
557-
kerror!("Failed to Remove Directory, Error Code = {:?}", err);
558579
return Err(err);
559580
}
560581
Ok(_) => {
@@ -563,9 +584,8 @@ impl Syscall {
563584
}
564585
}
565586

566-
match do_unlink_at(dirfd, &pathname) {
587+
match do_unlink_at(dirfd, &path) {
567588
Err(err) => {
568-
kerror!("Failed to Remove Directory, Error Code = {:?}", err);
569589
return Err(err);
570590
}
571591
Ok(_) => {
@@ -574,32 +594,14 @@ impl Syscall {
574594
}
575595
}
576596

577-
pub fn rmdir(pathname: *const u8) -> Result<usize, SystemError> {
578-
let pathname: String = check_and_clone_cstr(pathname, Some(MAX_PATHLEN))?;
579-
if pathname.len() >= MAX_PATHLEN {
580-
return Err(SystemError::ENAMETOOLONG);
581-
}
582-
let pathname = pathname.as_str().trim();
583-
return do_remove_dir(AtFlags::AT_FDCWD.bits(), pathname).map(|v| v as usize);
597+
pub fn rmdir(path: *const u8) -> Result<usize, SystemError> {
598+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
599+
return do_remove_dir(AtFlags::AT_FDCWD.bits(), &path).map(|v| v as usize);
584600
}
585601

586-
pub fn unlink(pathname: *const u8) -> Result<usize, SystemError> {
587-
if pathname.is_null() {
588-
return Err(SystemError::EFAULT);
589-
}
590-
let ureader = UserBufferReader::new(pathname, MAX_PATHLEN, true)?;
591-
592-
let buf: &[u8] = ureader.buffer(0).unwrap();
593-
594-
let pathname: &CStr = CStr::from_bytes_until_nul(buf).map_err(|_| SystemError::EINVAL)?;
595-
596-
let pathname: &str = pathname.to_str().map_err(|_| SystemError::EINVAL)?;
597-
if pathname.len() >= MAX_PATHLEN {
598-
return Err(SystemError::ENAMETOOLONG);
599-
}
600-
let pathname = pathname.trim();
601-
602-
return do_unlink_at(AtFlags::AT_FDCWD.bits(), pathname).map(|v| v as usize);
602+
pub fn unlink(path: *const u8) -> Result<usize, SystemError> {
603+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
604+
return do_unlink_at(AtFlags::AT_FDCWD.bits(), &path).map(|v| v as usize);
603605
}
604606

605607
/// # 修改文件名
@@ -892,45 +894,44 @@ impl Syscall {
892894
}
893895

894896
pub fn fstat(fd: i32, usr_kstat: *mut PosixKstat) -> Result<usize, SystemError> {
897+
let mut writer = UserBufferWriter::new(usr_kstat, size_of::<PosixKstat>(), true)?;
895898
let kstat = Self::do_fstat(fd)?;
896-
if usr_kstat.is_null() {
897-
return Err(SystemError::EFAULT);
898-
}
899-
unsafe {
900-
*usr_kstat = kstat;
901-
}
899+
900+
writer.copy_one_to_user(&kstat, 0)?;
902901
return Ok(0);
903902
}
904903

905-
pub fn stat(path: &str, user_kstat: *mut PosixKstat) -> Result<usize, SystemError> {
906-
let fd = Self::open(path, FileMode::O_RDONLY, ModeType::empty(), true)?;
904+
pub fn stat(path: *const u8, user_kstat: *mut PosixKstat) -> Result<usize, SystemError> {
905+
let fd = Self::open(
906+
path,
907+
FileMode::O_RDONLY.bits(),
908+
ModeType::empty().bits(),
909+
true,
910+
)?;
907911
let r = Self::fstat(fd as i32, user_kstat);
908912
Self::close(fd).ok();
909913
return r;
910914
}
911915

912-
pub fn lstat(path: &str, user_kstat: *mut PosixKstat) -> Result<usize, SystemError> {
913-
let fd = Self::open(path, FileMode::O_RDONLY, ModeType::empty(), false)?;
916+
pub fn lstat(path: *const u8, user_kstat: *mut PosixKstat) -> Result<usize, SystemError> {
917+
let fd = Self::open(
918+
path,
919+
FileMode::O_RDONLY.bits(),
920+
ModeType::empty().bits(),
921+
false,
922+
)?;
914923
let r = Self::fstat(fd as i32, user_kstat);
915924
Self::close(fd).ok();
916925
return r;
917926
}
918927

919928
pub fn mknod(
920-
path_ptr: *const i8,
929+
path: *const u8,
921930
mode: ModeType,
922931
dev_t: DeviceNumber,
923932
) -> Result<usize, SystemError> {
924-
// 安全检验
925-
let len = unsafe { CStr::from_ptr(path_ptr).to_bytes().len() };
926-
let user_buffer = UserBufferReader::new(path_ptr, len, true)?;
927-
let buf = user_buffer.read_from_user::<u8>(0)?;
928-
let path = core::str::from_utf8(buf).map_err(|_| SystemError::EINVAL)?;
929-
930-
// 文件名过长
931-
if path.len() > MAX_PATHLEN as usize {
932-
return Err(SystemError::ENAMETOOLONG);
933-
}
933+
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
934+
let path = path.as_str().trim();
934935

935936
let inode: Result<Arc<dyn IndexNode>, SystemError> =
936937
ROOT_INODE().lookup_follow_symlink(path, VFS_MAX_FOLLOW_SYMLINK_TIMES);
@@ -980,12 +981,9 @@ impl Syscall {
980981
buf_size: usize,
981982
) -> Result<usize, SystemError> {
982983
let path = check_and_clone_cstr(path, Some(MAX_PATHLEN))?;
984+
let path = path.as_str().trim();
983985
let mut user_buf = UserBufferWriter::new(user_buf, buf_size, true)?;
984986

985-
if path.len() == 0 {
986-
return Err(SystemError::EINVAL);
987-
}
988-
989987
let (inode, path) = user_path_at(&ProcessManager::current_pcb(), dirfd, &path)?;
990988

991989
let inode = inode.lookup(path.as_str())?;

0 commit comments

Comments
 (0)