-
-
Notifications
You must be signed in to change notification settings - Fork 176
feat(ext4): 添加move_to函数 #1758
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
feat(ext4): 添加move_to函数 #1758
Conversation
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
|
@codex review |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: fa307d6820
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
kernel/src/filesystem/ext4/inode.rs
Outdated
| // 目标必须是 LockedExt4Inode(同一文件系统) | ||
| let target_locked = target | ||
| .clone() | ||
| .downcast_arc::<LockedExt4Inode>() | ||
| .ok_or(SystemError::EXDEV)?; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Reject cross-mount renames before using ext4 fs
The downcast only proves target is a LockedExt4Inode, not that it belongs to the same Ext4FileSystem. If target is from another ext4 mount, the code will pass that inode number into the source filesystem (ext4_fs.fs), which can corrupt or misaddress inodes instead of returning EXDEV. Please compare concret_fs() (or an fs id) between self and target_locked and return EXDEV when they differ.
Useful? React with 👍 / 👎.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
这个在另一个pr里面解决了
kernel/src/filesystem/ext4/inode.rs
Outdated
| } | ||
| } | ||
| ext4.unlink(target_inode_num, new_name)?; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Avoid deleting destination before a failing rename
When the destination exists you remove it (unlink/rmdir) before calling ext4.rename. The underlying ext4 rename can still fail (e.g., ENOSPC or I/O), so this sequence can lose the original destination entry even though the rename didn’t happen. Linux rename is atomic w.r.t. replacement; the destination should remain unchanged if the rename fails. Consider performing the replacement inside a single ext4 operation or ensure rollback when ext4.rename fails.
Useful? React with 👍 / 👎.
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
|
想要真正实现原子性还是得日志系统。 |
|
ext4的更改需要补充充分的测试用例。那个库可以单独cargo test的。 |
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
- 新增rename_exchange方法实现原子交换两个目录项 - 添加辅助函数read_rename_dirs和check_ancestor_cycle - 在VFS层添加EXCHANGE标志处理和缓存更新逻辑 - 遵循POSIX语义实现目录循环检测和跨目录处理 Signed-off-by: xboHodx <xbohodx2024@gmail.com>
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
- 新增rename_exchange_test函数测试文件/目录交换功能 - 修改BlockFile实现使用Box包装buffer - 在Cargo.toml中添加workspace配置 Signed-off-by: xboHodx <xbohodx2024@gmail.com>
| let _r = file.read_exact(&mut buffer); | ||
| Block::new(block_id, buffer) | ||
| Block::new(block_id, Box::new(buffer)) | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
这里为什么要多一次动态内存分配?性能损失
| assert_eq!(names, vec!["user.testtwo"]); | ||
| } | ||
|
|
||
| fn rename_exchange_test(ext4: &mut Ext4) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
测试写单独文件里面去,这个main太长了。
| [workspace] | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
清理
|
@codex review,尤其是看看正确性、并发安全、有没有TOCTOU问题、有没有性能可优化的地方 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 153058aacc
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| // NOREPLACE check (VFS layer responsibility - ext4 lib doesn't know about flags) | ||
| if flags.contains(RenameFlags::NOREPLACE) && ext4.lookup(target_inode_num, new_name).is_ok() | ||
| { | ||
| return Err(SystemError::EEXIST); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Avoid TOCTOU in RENAME_NOREPLACE handling
The NOREPLACE path checks ext4.lookup() and then later calls ext4.rename() without holding a filesystem lock or passing the flag down, so a concurrent creator can race between the check and the rename. In that case renameat2(..., RENAME_NOREPLACE) will incorrectly overwrite an existing target, which violates Linux semantics. This is a true TOCTOU introduced by moving atomic-replace behavior into ext4 and keeping NOREPLACE only as a VFS pre-check; the filesystem needs to enforce NOREPLACE atomically or provide a locked rename-with-flags path.
Useful? React with 👍 / 👎.
| if existing_is_dir { | ||
| self.dir_remove_entry(&existing_inode, "..")?; | ||
| target_dir |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do not delete
.. in replaced directory
When replacing an existing empty directory, the implementation removes the .. entry from the replaced directory before dropping its link count. If that directory is still reachable via an open fd or is the process’s cwd, Linux keeps .. valid even after unlink/rmdir; removing it makes .. lookups fail or behave inconsistently. The correct behavior is to adjust link counts and remove the parent’s entry, but leave the directory’s .. entry intact until the inode is fully freed.
Useful? React with 👍 / 👎.
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
Signed-off-by: xboHodx <xbohodx2024@gmail.com>
- 移除link.rs中冗余的目录".."删除操作 - 重构low_level.rs中的rename逻辑,使其更接近Linux ext4实现 - 优化目录移动时的link count处理流程 Signed-off-by: xboHodx <xbohodx2024@gmail.com>
- 取消注释所有被注释的测试代码段 - 确保所有测试用例都能正常执行 Signed-off-by: xboHodx <xbohodx2024@gmail.com>
2026/2/5
Summary
RENAME_EXCHANGE支持,实现原子交换两个目录项move_to接口,包含缓存一致性管理详细变更
1. ext4 底层 rename 实现 (
another_ext4/src/ext4/low_level.rs)原子替换语义:当目标已存在时,不再返回
EEXIST,而是按 POSIX 标准原子替换:..的 link_count 变更循环检测:新增
check_ancestor_cycle()辅助函数,防止把目录移动到自己的子目录下(返回EINVAL)新增
rename_exchange():实现RENAME_EXCHANGE标志功能,原子交换两个目录项的 inode 引用2. 目录操作扩展 (
another_ext4/src/ext4/dir.rs,ext4_defs/dir.rs)dir_replace_entry(): 原地替换目录项的 inode(原子操作核心)dir_is_empty(): 检查目录是否为空(仅含.和..)DirEntry::set_inode(): 修改目录项 inode 号3. VFS 层集成 (
kernel/src/filesystem/ext4/inode.rs)实现
IndexNode::move_to()trait 方法:RENAME_NOREPLACE和RENAME_EXCHANGE标志truncate_inode_pages)update_rename_cache()和update_exchange_cache()正确更新 children 映射和 parent引用
4. VFS syscall 层 (
rename_utils.rs)EXCHANGE与NOREPLACE/WHITEOUT互斥RENAME_EXCHANGE前置检查:目标必须存在5. 测试 (
user/apps/c_unitest/test_rename.c)约 1000 行全面测试,覆盖:
RENAME_NOREPLACE/RENAME_EXCHANGE标志./..处理等)