编译器如何理解你的代码
原理
Rust 编译器工作流程:
源码 (.rs)
→ Lexer/Parse → AST (abstract syntax tree)
→ HIR (high-level IR): 宏展开后、类型推导前的 IR
→ MIR (mid-level IR): 控制流图形式,borrow check、drop elaboration、优化
→ LLVM IR: SSA 形式的底层表示
→ 目标平台机器码
HIR 阶段:AST → 高层表示,保留 Rust 语义。用于类型推导和 trait 解析。
MIR 阶段(关键):将 HIR 降级为控制流图。这是 borrow checker、NLL(non-lexical lifetimes)分析、drop 插入、常量求值的舞台。MIR 是 Rust 安全保证的核心编译阶段。
LLVM IR 阶段:MIR → LLVM IR。LLVM 执行优化 pass(内联、循环展开、noalias 利用、SIMD 向量化等)。-C opt-level=3 控制优化力度。
rust-analyzer 使用 libsyntax2 提供 IDE 级别的实时分析(不完整编译,仅增量分析)。
Cargo 的增量编译:MIR 单元按函数粒度缓存,只重编译有变化的函数。Clean build vs incremental:增量编译在 10%~50% 的时间完成。
语法
查看 MIR
rustc --emit mir main.rs查看 LLVM IR
rustc --emit llvm-ir main.rs查看汇编
rustc --emit asm -C opt-level=3 main.rs编译器标志速查
| 标志 | 作用 |
|---|---|
-C opt-level=0..3/s/z | 优化级别 |
-C debuginfo=0..2 | 调试信息 |
-C lto=fat/thin | 链接时优化 |
-C panic=abort/unwind | panic 行为 |
-C target-cpu=native | 目标 CPU 优化 |
-Z time-passes | 编译时间分析 |
lint 级别
#[deny(warnings)]
#[allow(unused_variables)]
#[warn(missing_docs)]实践
AI 自检
- MIR 和 LLVM IR 的根本区别?为什么 borrow checker 在 MIR 层而非 LLVM IR 层?
- ThinLTO 和 full LTO 的区别?增量编译时 LTO 如何处理缓存?