|
| 1 | +--- |
| 2 | +name: dragonos-develop-nix-yolo-boot-check |
| 3 | +description: 专用于按照 docs/introduction/develop_nix.md 的流程,通过 Nix dev shell / yolo 命令启动 DragonOS,并在 QEMU nographic 串口中做启动烟雾检查或实时轮询回贴输出。当用户要求“按 develop_nix 跑 yolo”“用 nix yolo 启动 QEMU 看输出”“边跑边轮询输出”“进 guest 后检查 /proc、/sys/fs/cgroup、mount 是否正常”时使用。 |
| 4 | +--- |
| 5 | + |
| 6 | +# DragonOS Develop Nix Yolo Boot Check |
| 7 | + |
| 8 | +## 目标 |
| 9 | + |
| 10 | +按项目文档的推荐路径启动 DragonOS: |
| 11 | + |
| 12 | +1. 走 `develop_nix` 对应的 Nix 环境 |
| 13 | +2. 运行 `nix run .#yolo-x86_64 -- -nographic` |
| 14 | +3. 在 QEMU 串口里观察启动日志 |
| 15 | +4. 进入 guest shell 做最小烟雾检查 |
| 16 | +5. 把成功信号、失败点和原始报错带回给用户 |
| 17 | +6. 如果用户要求“边跑边看/实时输出”,持续轮询 PTY 并回贴最新输出块 |
| 18 | + |
| 19 | +## 何时使用 |
| 20 | + |
| 21 | +- 用户明确提到 `develop_nix`、`nix develop`、`yolo-x86_64` |
| 22 | +- 用户要求“启动 DragonOS 看输出” |
| 23 | +- 用户要求“进 QEMU 里手动检查” |
| 24 | +- 内核改动后,需要快速确认系统是否还能完整启动到用户态 |
| 25 | + |
| 26 | +## 前置检查 |
| 27 | + |
| 28 | +1. 先读 `docs/introduction/develop_nix.md`,确认文档仍然推荐: |
| 29 | + - `nix develop` |
| 30 | + - `make kernel` |
| 31 | + - `nix run .#rootfs-x86_64` |
| 32 | + - `nix run .#start-x86_64` |
| 33 | + - 以及一键命令 `nix run .#yolo-x86_64` |
| 34 | +2. 先看 `git status --short`,记住当前工作树是脏还是干净。 |
| 35 | +3. 如果写磁盘镜像会触发 `sudo`,而用户已经给了密码,可以先预热 sudo;如果没有给密码,要先向用户说明会卡在提权步骤。 |
| 36 | +4. 注意 `yolo` 的 `rootfs`/QEMU 阶段都可能在较晚时再次调用 `sudo`。单次 `sudo -v` 可能在长时间依赖下载或 rootfs 构建后过期,不要假设一次预热就够。 |
| 37 | + |
| 38 | +## 推荐执行顺序 |
| 39 | + |
| 40 | +### 1) 预热 sudo,并优先使用 keepalive |
| 41 | + |
| 42 | +如果用户已经提供密码,优先在和 `yolo` 相同的 PTY 会话里维持 sudo 时间戳: |
| 43 | + |
| 44 | +```bash |
| 45 | +sudo -v |
| 46 | +while true; do sudo -n true; sleep 60; done 2>/dev/null & |
| 47 | +keeper=$! |
| 48 | +trap 'kill $keeper' EXIT |
| 49 | +nix run .#yolo-x86_64 -- -nographic |
| 50 | +``` |
| 51 | + |
| 52 | +如果只是单独预热: |
| 53 | + |
| 54 | +```bash |
| 55 | +printf '%s\n' "$PASSWORD" | sudo -S -v |
| 56 | +``` |
| 57 | + |
| 58 | +也不要把它当成足够稳妥的方案,因为 `rootfs` 写盘和 `start-x86_64` 往往会在较晚阶段再次触发 `sudo`。 |
| 59 | + |
| 60 | +如果没有密码,不要假设;直接告诉用户这一步会阻塞在提权提示。 |
| 61 | + |
| 62 | +如果在沙箱里看到类似: |
| 63 | + |
| 64 | +```text |
| 65 | +sudo: The "no new privileges" flag is set |
| 66 | +``` |
| 67 | + |
| 68 | +这说明是宿主机/沙箱权限边界,不是 DragonOS 回归;应改为在沙箱外执行同一命令。 |
| 69 | + |
| 70 | +### 2) 用 PTY 启动 yolo |
| 71 | + |
| 72 | +必须用带 TTY 的终端会话运行: |
| 73 | + |
| 74 | +```bash |
| 75 | +nix run .#yolo-x86_64 -- -nographic |
| 76 | +``` |
| 77 | + |
| 78 | +要点: |
| 79 | + |
| 80 | +- 必须使用交互式 PTY,否则后续无法和 QEMU 串口交互。 |
| 81 | +- 如果用户提供了密码且预期会构建较久,优先使用“同 PTY 的 sudo keepalive + yolo”这一条组合命令,而不是裸跑 `nix run .#yolo-x86_64 -- -nographic`。 |
| 82 | +- 这条命令会顺序执行: |
| 83 | + - `make kernel` |
| 84 | + - `nix run .#rootfs-x86_64` |
| 85 | + - `nix run .#start-x86_64 -- -nographic` |
| 86 | +- 允许出现 host CPU / KVM feature warning,只要系统继续启动,不把这些 warning 当成失败。 |
| 87 | + |
| 88 | +### 3) 如果用户要求实时输出,持续轮询并回贴原始输出块 |
| 89 | + |
| 90 | +如果用户明确要求“边跑边轮询”“实时输出”“一边跑一边给我看”,不要只在最后总结;应在整个过程中轮询 PTY 并回贴最新输出。 |
| 91 | + |
| 92 | +要点: |
| 93 | + |
| 94 | +- 这个界面不会自动把 PTY 原始流直接推给用户;需要手动轮询会话并回贴输出块。 |
| 95 | +- 活跃阶段(编译、rootfs 写盘、串口刷屏)可用 1-5 秒轮询;长时间静默构建阶段可放宽到 10-30 秒。 |
| 96 | +- 优先贴“最新一块原始输出 + 一句简短说明”,不要只做抽象总结。 |
| 97 | +- 对真正的错误、warning、panic、mount 失败,尽量保留原文,不要改写掉关键报错。 |
| 98 | +- 如果是大段宿主机构建日志,抓关键窗口即可;如果是 guest 串口异常,优先贴第一处异常附近的原始日志。 |
| 99 | +- 如果用户没有要求实时输出,仍然要在关键阶段给出简洁进度,但不必高频贴日志。 |
| 100 | + |
| 101 | +### 4) 观察启动阶段的关键成功信号 |
| 102 | + |
| 103 | +重点盯以下日志: |
| 104 | + |
| 105 | +- `Kernel Build Done.` |
| 106 | +- `Build complete!` |
| 107 | +- `Step 3: Starting DragonOS...` |
| 108 | +- `DragonOS release ...` |
| 109 | +- `ProcFS mounted at /proc` |
| 110 | +- `SysFS mounted.` |
| 111 | +- `Cgroup2 mounted at /sys/fs/cgroup` |
| 112 | +- `Successfully migrate rootfs to ext4!` |
| 113 | +- `Boot with specified init process` |
| 114 | +- `root@dragonos:~#` 或等价 shell prompt |
| 115 | + |
| 116 | +如果看到 panic、`init` 启动失败、mount 失败、卡死在早期阶段,要把原始日志摘出来。 |
| 117 | + |
| 118 | +### 5) 激活 guest 控制台 |
| 119 | + |
| 120 | +有些镜像会提示: |
| 121 | + |
| 122 | +```text |
| 123 | +Please press Enter to activate this console. |
| 124 | +``` |
| 125 | + |
| 126 | +这时向 PTY 写入一个换行: |
| 127 | + |
| 128 | +```text |
| 129 | +\n |
| 130 | +``` |
| 131 | + |
| 132 | +直到出现 shell prompt。 |
| 133 | + |
| 134 | +### 6) guest 内最小烟雾检查 |
| 135 | + |
| 136 | +默认执行下面几条,逐条记录结果: |
| 137 | + |
| 138 | +```bash |
| 139 | +cat /proc/self/cgroup |
| 140 | +cat /proc/mounts | grep cgroup |
| 141 | +ls /sys/fs/cgroup |
| 142 | +``` |
| 143 | + |
| 144 | +如果这次任务和 cgroup/mount 相关,再补: |
| 145 | + |
| 146 | +```bash |
| 147 | +mkdir /sys/fs/cgroup/testcg |
| 148 | +ls /sys/fs/cgroup/testcg |
| 149 | +cat /sys/fs/cgroup/testcg/cgroup.procs |
| 150 | +``` |
| 151 | + |
| 152 | +注意: |
| 153 | + |
| 154 | +- 如果你在通过 PTY/串口逐条喂命令,优先“一次写一条命令,等 prompt 回来后再发下一条”。不要把多条命令一次性塞给 guest,否则串口可能吞字、错行或把后续命令打坏。 |
| 155 | +- 不要把“命令执行了”误写成“功能通过了”。 |
| 156 | +- 如果写文件时报 `Function not implemented`、`Permission denied`、`No such file or directory`,要原样记录。 |
| 157 | +- 如果 shell 卡住,先看是不是命令本身阻塞,不要立即判成内核 panic。 |
| 158 | + |
| 159 | +### 7) 退出 QEMU |
| 160 | + |
| 161 | +在 nographic 模式下,退出序列是: |
| 162 | + |
| 163 | +```text |
| 164 | +Ctrl+A 然后 x |
| 165 | +``` |
| 166 | + |
| 167 | +向 PTY 写入: |
| 168 | + |
| 169 | +```text |
| 170 | +\u0001x |
| 171 | +``` |
| 172 | + |
| 173 | +## 默认报告格式 |
| 174 | + |
| 175 | +```markdown |
| 176 | +## Develop Nix Yolo Boot Check |
| 177 | + |
| 178 | +### 宿主机阶段 |
| 179 | +- 是否成功进入 Nix 路径 |
| 180 | +- 是否成功完成 kernel / rootfs / disk image / QEMU 启动 |
| 181 | + |
| 182 | +### QEMU 启动结果 |
| 183 | +- 是否进入用户态 shell |
| 184 | +- 关键日志 |
| 185 | + |
| 186 | +### Guest 烟雾检查 |
| 187 | +- `cat /proc/self/cgroup` => ... |
| 188 | +- `cat /proc/mounts | grep cgroup` => ... |
| 189 | +- `ls /sys/fs/cgroup` => ... |
| 190 | +- 额外检查 => ... |
| 191 | + |
| 192 | +### 结论 |
| 193 | +- 启动是否通过 |
| 194 | +- 哪些子路径通过 |
| 195 | +- 哪些子路径失败,原始错误是什么 |
| 196 | +``` |
| 197 | + |
| 198 | +如果用户要求实时输出,可在过程中的每一轮更新里采用: |
| 199 | + |
| 200 | +````markdown |
| 201 | +最新输出块: |
| 202 | + |
| 203 | +```text |
| 204 | +... |
| 205 | +``` |
| 206 | + |
| 207 | +一句话说明当前阶段 / 下一步。 |
| 208 | +```` |
| 209 | + |
| 210 | +## 失败处理 |
| 211 | + |
| 212 | +- 如果失败发生在 `sudo` 提权:明确说明是宿主机权限问题,不是内核回归。 |
| 213 | +- 如果失败是 `sudo: timed out reading password`,且位置在 rootfs 写盘或 QEMU 启动之前/之中,优先判定为“长流程中的 sudo 交互超时”;应改为“同 PTY keepalive + 重跑”,不要误判成 rootfs 或内核 bug。 |
| 214 | +- 如果失败发生在 `make kernel`:返回编译错误摘要和首个真正报错点。 |
| 215 | +- 如果失败发生在 `rootfs` / 磁盘镜像:返回宿主机构建错误,不要误判为 guest 启动失败。 |
| 216 | +- 如果失败发生在 QEMU 内:优先保留串口日志里的第一处异常。 |
| 217 | + |
| 218 | +## 边界约束 |
| 219 | + |
| 220 | +- 默认使用 `x86_64`,除非用户明确指定其他架构。 |
| 221 | +- 默认遵循 `docs/introduction/develop_nix.md`,不要擅自切回旧的非 Nix 路径。 |
| 222 | +- 如果只是做“能否编译”的快速检查,优先 `nix develop -c make kernel`;只有用户要求真实启动或需要 guest 内验证时才走 yolo。 |
0 commit comments