Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
---
title: 2025秋冬季开源操作系统训练营-第三阶段总结-郑泉城
date: 2025-11-16 19:26:30
tags:
- author: ZhengQuancheng
mathjax: true
---

## lab1: print_with_color
- 本实验比较较为简单, 修改 `arceos/exercises/print_with_color/src/main.rs` 文件, 为 `println` 添加 ANSI 转义码即可. ANSI 转义码用于在终端中控制光标位置、文本颜色、文本样式等, 其以 ESC (Escape) 字符开头.
- 初次在 Rust 中使用 `\033[34m[WithColor]: Hello, Arceos!\033[0m` 形式的 ANSI 转义码, 发现其不奏效; 但是在 C/C++ 中却是正常. 查阅资料后得知, `\033` 是 C 语言的传统写法, 在 C/C++ 中使用较多. 在 Rust 中, 应该使用 `\x1b`, 即 `\x1b[34m[WithColor]: Hello, Arceos!\x1b[0m`. 本是上来说, `\033` 和 `\x1b` 是同一内容的不同表示.

## lab2: support_hashmap
- 本实验直接使用 `hashbrown` 来支持 `hashmap`. 在 `arceos/ulib/axstd/Cargo.toml` 中添加 `hashbrown` 依赖, 在 `axstd` 中添加 `collections` 模块, 并在 `arceos/ulib/axstd/Cargo.toml` 中声明 `pub mod collections;`. 在 `collections` 模块中, 使用 `pub use alloc::collections::*;`, 将 `alloc::collections` 的内容(比如 `BTreeMap`)导入当前的模块, 使用 `pub use hashbrown::*;` 将第三方库的 `HashMap` 等导入当前模块, 此时可以通过 `axstd::collections` 使用 `HashMap`(`hashbrown` 提供)、`BTreeMap`(`alloc::collections` 提供).
- 还有一点要注意, 应该在启用 `alloc` feature 时才会声明并挂载 `collections` (#`[cfg(feature = "alloc")]`), 若不加以控制, `print_with_color` 则会出现报错. 原因在于, 若 `collections` 的编译不被 `alloc` feature 控制, 其中的 `BTreeMap` 等会依赖全局内存分配器, 但是因没有启用 `alloc` feature, 故而找不到全局内存分配器. 应该启用 `alloc` feature 时才会编译 `collections`.

## lab3: alt_alloc
- 此实验是实现简单的内存分配器, 在 `arceos/modules/alt_axalloc/src/lib.rs` 中具体实现.
- `arceos/exercises/alt_alloc/Cargo.toml` 声明依赖 `axstd`: `workspace = true` 表明 `axstd` 是工作区成员; `features = ["alt_alloc"]` 使 `axstd` 开启 `alt_alloc` 特性. 当 `axstd` 的 `alt_alloc` 特性被启用时, 其会继续将此传递下去, 还会根据 `[features]` 的 `alt_alloc = ["arceos_api/alt_alloc", "axfeat/alt_alloc"]` 启用 `arceos_api` 中的 `alt_alloc` 特性和 `axfeat` 中的 `alt_alloc` 特性.

## lab4: ramfs_rename
- 实验要求在 `arceos/axfs_ramfs` 中实现 `rename` 操作, 但 arceos 原本依赖远程仓库的版本, 故需要调整.
- 可以采用 patch 方式让工程临时使用 `arceos/axfs_ramfs` 的本地组件仓库. 为方便起见, 直接在 `arceos/exercises/ramfs_rename/Cargo.toml` 中将 `axfs_ramfs = { version = "0.1", optional = true }` 中的 `version = "0.1"` 替换为 `workspace = true`, 多次运行发现还是提示 **Operation not supported**. 然后对代码进行详细分析, 发现应用 `ramfs_rename` 会依赖 `axfs`(间接) 和 `axfs_ramfs`, `axfs` 还会依赖 `axfs_ramfs`, 此时 `ramfs_rename` 依赖的 `axfs_ramfs` 与 `axfs` 依赖的不同. 故还需将修改 `arceos/modules/axfs/Cargo.toml`, 替换 `version = "0.1"` 为 `workspace = true`.
- 具体实现 rename 功能, 只需修改 `arceos/axfs_ramfs/src/dir.rs`. 阅读测试用例后发现, 文件重命名只在同一个目录下操作, 故在具体实现中只考虑此情况, 并未做特殊处理.

## lab5: sys_map
- 初次运行 `sys_map` 时, 发现运行结果与课件中展示的内容有很大出入, 课件显示 `not implement`, 而本地运行则会显示 `Cannot load app!`. 经排查, 发现未设置 `musl-libc`, 导致无法编译出 `mapfile` 可执行文件.
- 实现 `sys_map` 时针对测试用例做了简化处理, 未考虑复杂的情况. 实现 `sys_mmap` 系统调用主要有 5 个步骤: 获取当前进程的地址空间, 并在此查找空闲内存区域, 再准备参数执行内存映射, 再读取文件内容到缓冲区 buf 并将其写入映射的内存区域, 最后返回映射起始位置. 实现过程中, 务必查找空闲的内存区域再映射, 否则会出现 `Mapping error: AlreadyExists`.

## lab6: simple_hv
- 运行此实验代码, 发现QEMU会卡死. 经过仔细排查, 是由于 `payload` 构建失败导致的. 在外层 Makefile 中定义的 `RUSTFLAGS` 会被默认传递给 `make -C ./payload` 递归调用, 这会干扰编译 `payload` (尤其是 skernel). 故在 `payload` 的 `Makefile` 中添加 `unexport RUSTFLAGS` 来避免 RUSTFLAGS 变量的传播.
- 正常运行后, 根据 `panic` 指示修改实现, 使测例通过即可. 在异常处理分支中, panic 改为 `ax_println`, 还要调整客户机的 `spec`, 即 `ctx.guest_regs.sepc += 4;`. 注意, 还要设置 `A0` 寄存器的值为 `0x6688`, `A1` 寄存器的值为 `0x1234`.