Files
Interpreter/Doc/vm/扫描周期.md
T

71 lines
3.8 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 扫描周期
vm 模块:寄存器虚拟机(V2:变长指令 / 槽表两级 / 栈方案 C)。CMake 目标:`vm``STATIC`),只依赖 [`指令与映像.md`](../isa/指令与映像.md)。
运行时是 **一台 VM、一个入口、一份映像**。不链接 `compiler`。扫描周期与确定性见 [`初步计划.md`](../初步计划.md) 第 2、8 节。
## 扫描周期
```text
1. 按 sidecar 的 io 绑定,采样 → I / 输入全局(executor 写值区槽)
2. 从 PROGRAM MAIN 的 pc=0 执行到 RET
3. 写回 Q / 输出全局(executor 读值区槽)
4. 用本周期 Δt(映像头 dt_ms)推进内置 FB(不用 wall clock);RTC 用累计周期数
```
## 边界
- 只认 `.stb` 映像(`vm` 自带读实现);读取时**型号标识匹配(STATOR2+ SHA-256 校验**,不符/篡改 → 拒绝
- 类型与溢出按 [`指令与映像.md`](../isa/指令与映像.md)(整数饱和 / 除法 A / 浮点 IEEE);指令定义归 `isa`
- 局部 / `VAR` = 固定寄存器;`nregs` 在函数头;栈区预分配(`max_stack`,编译期 DAG 最坏路径)
- `CALL` 目标是立即数 `fn_id`,有界调用栈(深度 64 双检查)
- 无 GC、无堆、无线程;每周期受 `cycle_limit` 限制
- I/O 从哪来、Δt 谁给、回放怎么喂,属于 `BytecodeExecutor`(读 `.stb` + sidecar
---
## 可观察性接口(v1 预留)
TUI 是执行器(`BytecodeExecutor`)的界面,用途是方便观察 VM 运行状态。**v1 不做 TUI**,只预留接口,避免后续改 VM 的观察面。原则:
- **数据与展示分离**`vm` 只提供只读观察 API(数据);TUI 渲染与文本输出属于 `executor`(展示)。vm 不画任何界面。
- **只读轮询**:TUI 通过快照轮询,绝不写 VM 状态;"继续 / 单步"是 executor 侧命令,不改变确定性。
- **快照 POD 化**:快照保持简单数据(将来跨进程 TUI 可序列化)。
已落地的观察面(`Machine` 公共接口):
```cpp
bool step(); // 精确执行一条指令,停在指令边界
Fault fault() const; // 最近一次故障
bool ended() const; // 周期是否已结束
uint32_t pc() const; // 当前 pc(字节,相对本帧函数)
uint32_t fn_id() const; // 当前函数
uint32_t cycle_count() const; // 本周期已执行指令数
uint32_t call_depth() const; // 调用栈深度
uint8_t* data(); // 值区(I 采样 / Q 读回由外部做)
uint32_t slot_addr(uint32_t slot) const; // 槽 → 值区偏移(槽表两级)
int64_t reg(uint8_t i) const; // 当前帧寄存器
const uint8_t* cur_instr_bytes() const; // 当前指令首字节(单步反汇编用)
uint32_t cur_instr_len() const; // 当前指令长度(变长)
```
- 寄存器 ≤256、映像很小,快照拷贝成本可忽略。
- 单步、回放、dump 都建立在同一套观察 API 上。
---
## V2 落地状态
| 项 | 状态 |
|---|---|
| 变长取指(4/8/16/32B,前缀分区)+ 字节 pc | ✅ `Machine.cpp` exec_one |
| 槽表两级(slot → addr → 值区变宽紧凑)+ LOAD_OFF/STORE_OFF | ✅ |
| 栈方案 C(预分配 max_stack、帧头 12B、r0..r7 复制、深度 64 双检查) | ✅ do_call/do_ret |
| 19 类型 func 驱动(整数饱和 / 无符号 / F32 / F64 IEEE | ✅ exec_arith/exec_cmp |
| CAL 15 条(TON/TOF/TP/CTU/DCTU/CTD/DCTD/CTUD/DCTUD/R_TRIG/F_TRIG/SR/RS/PWM/RTC | ✅ do_cal |
| 故障(None/CycleLimit/StackOverflow/BadOp/BadSlot/BadConst | ✅ |
| 边沿缓冲 edge_prev_(每槽 2 字节,跨周期) | ✅ |
| 确定性:同一 I 序列跑两遍,数据区完全一致 | ✅ vm_test |
指令执行语义(帧/调用栈、指令表、定时器、故障、line1 推演)见 [`指令执行.md`](指令执行.md)。