Files

100 lines
6.7 KiB
Markdown

# I2C-Lab AGENTS.md — 工程约束与开发进度
> 面向 Agent/开发者的工程档案。使用说明见 `README.md`; 仓库整体进度见根
> `agent.md`。遵循全仓约定: 三区目录(src 人写 / assets 可再生 / release 交付)、
> Python 3.14 + PySide6-Fluent-Widgets、纯标准库协议模块、PyInstaller onefile。
## 1. 项目约定
- **定位**: I2C 总线监控调试台(2026-10-02 启动, 原 §3.5 三合一需求)。
第一阶段 = 纯被动监控; 主机/从机为后续阶段(见 README §7)。
- **与 I2C-Inject 关系**: I2C-Inject 保持"暂停开发, 留档备查"状态不复活;
本工具是新开的独立目录, 吸收其资产(接线规矩 GP8/9、`=`/`!` 回显约定、
解码算法、图标母题), 主机阶段落地后取代其"注入"职能。
- **解码语义权威是 `src/i2cdec.py`**(算法源自 I2C-Inject `i2c_sniff_decode.py`
真机验证版本): 固件 `main.c` 的解码状态机与它的 `decode_edges()` 必须语义
一致; T/W 行语法以 `to_tline()/parse_tline()/parse_wline()` 为准, 改任一侧
必须同步另一侧并补 selftest 向量。
- **时间戳约定**: 单位 us(int/u32); t0=START 沿, t1=收尾沿(STOP/rep-START/
最后边沿); 边沿 pins 编码 bit0=SDA bit1=SCL(GP8/GP9)。
- **固件架构**: 单 PIO SM `bus_watch`(变沿即压 FIFO, `push noblock`) +
核1 取时间戳并跑解码状态机(与 GUI 解码同语义) + 核0 USB CDC 命令行。
250MHz/vreg 1.15V。修改引脚/波特/协议时注意 `README.md` §5 与 GUI 同步。
- **pyserial 是唯一第三方运行依赖**(缺失降级提示); GUI/解码全标准库+PySide6。
- **release/ 交付物不入库**(2026-10-13 起全仓统一: `.gitignore` 全局挡 `*.exe`):
exe/UF2/BIN/zip 留本地, 待真机验收正式发布时再走流水线(`.gitignore` 已挡
`I2C-Lab/release/`)。
## 2. 构建
### PC 端
```powershell
cd src
python selftest.py ; python selftest_gui.py # 改 i2cdec/main 后必跑
python main.py --seconds 5 # GUI 冒烟
python main.py --seconds 5 --demo # 演示模式冒烟(无硬件)
python build_exe.py ; python package_release.py 0.1.0
python publish_gitea.py ../release/I2C-Lab-v0.1.0-win64.zip --insecure
```
### 固件(见 README §6)
pico-sdk 2.3.1 + tinyusb(锁定提交) + Arm GNU 13.3 + CMake/Ninja;
UF2 用 `make_uf2.py`(**不要**加 `pico_add_extra_outputs`, 会拉 picotool)。
## 3. 开发进度
### v0.1.0(2026-10-02, 未发布——待真机验收)
- 固件: bus_watch.pio(8 指令边沿捕获) + main.c 双核(核1 解码+事务环+边沿环,
核0 CLI + T/W 流), 命令 ?/v/mon/stats/wave/boot; 长事务 56 字节截断('L');
疑似丢沿统计(双位同变启发); wave 快照期间边沿环暂停(有缺口, 已注释)。
- PC 端: i2cdec.py(解码/T行/W行/CSV/编码器) 73 项自测全绿(含 100k/400k
往返、随机鲁棒、截断标志); probelink.py(行协议链路线程); waveview.py
(QPainter 波形); main.py(Fluent 双栏 GUI, 演示模式); theme/config 同源适配;
selftest_gui.py 29 项全绿; build/package/publish 三件套适配; exe 已打包。
- UF2 生成链: objcopy + make_uf2.py(往返自检 + 与真机 MicroPython UF2
逐字段核对通过); 产物保留本地 release/firmware/(交付物不入库, 见 §1 项目约定)。
### 待真机验收清单(下次接板)
- [ ] BPI-Pico 刷 UF2, USB CDC 枚举, `v`/`stats` 回显
- [ ] 挂 demo 板(LT8619C)实听: T 行滚动, 与已知轮询周期(~500ms)对照
- [ ] 0x606E 位交换注入用 SerialMate/旧工具对照, I2C-Lab 监控读数一致
- [ ] wave 快照在 400kHz 下波形完整, 缩放/注记正常
- [ ] 长时间(≥30min)挂机: trans_drop/susp 不增长
- [ ] 验收后: 打 tag `I2C-Lab-v0.1.0` → package → publish(含 UF2)
## 4. 已提出、尚未实现(路线)
- 主机模式: 硬件 I2C 主机 + I2C-Inject 择机注入语义(静置窗口/重试/读回
校验), GUI 寄存器读写卡 + 总线扫描; 命令 wr/rd/scan。
- 从机模拟: 硬件 I2C 从机 + PC 应答表(寄存器值由 GUI 配置/回调)。
- 监控增强: 协议语义插件(LT8619C bank/寄存器注释)、触发条件抓取、
长记录落盘、SMBus(PEC)注记、10bit 地址识别(目前按 7bit 解)。
- 波形增强: 按事务/地址着色、位级数值标注(需边沿级重解码——已具备)。
## 5. 踩坑表(勿重蹈)
| # | 问题 | 教训 |
|---|---|---|
| 1 | 解码器位缓冲在第 8 位清零 | 应凑满 9 位(8 数据+1 应答)才清——首版把 ACK 位错并进下一字节(数据整体右移一位); selftest 往返向量当场抓住 |
| 2 | 事务 acks 数量约定 | acks = 地址应答 + 每数据字节一个(共 n+1); 读事务末字节应答是主机发的 NAK, 造测试向量时别多写 |
| 3 | pico-sdk 2.x 板名 | `rpipico` 已更名 `pico`, 用 `-DPICO_BOARD=pico` |
| 4 | SDK 2.x UF2 依赖 picotool | `pico_add_extra_outputs` 会 FetchContent 拉 github(本机不通); 去掉该行, 用 objcopy+make_uf2.py; UF2 块布局用真机 UF2 解剖核对(偏移 20=blockNo 24=numBlocks 28=familyID), 别按记忆写 |
| 5 | pioasm 需要宿主 C++ 编译器 | 本机无 VS/mingw; 解法: `pip install ziglang`, 在 firmware/build/pioasm 预置 CMakeCache.txt, `CMAKE_CXX_COMPILER:STRING=<zig.exe 路径>;c++;-target;x86_64-windows-gnu;-static`(分号列表, 直接设 CXX 环境变量 CMake 不认) |
| 6 | ghproxy/gitclone 代理稳定性 | ghproxy.net 的 git 协议可用但大仓库会超时(pico-sdk 成功, picotool 两次超时); gitee.com/mirrors/tinyusb 是稳的; 环境变量 CXX 多词值 CMake 报 "Could not find compiler" |
| 7 | CDC 流控假设 | T 行流只在 `mon start` 且 USB 已连接时输出; wave 快照期间边沿环有缺口(暂停写入换一致性), 展示层要容忍 |
| 8 | CMD %ERRORLEVEL% 陷阱 | `cmd1 && cmd2 & echo %ERRORLEVEL%` 的 %ERRORLEVEL% 在解析期展开(恒为旧值); 管道 `findstr` 的退出码也会顶掉 git 的 |
| 9 | PySide6 实例级枚举访问 | `palette().color(pal.Base)` 在 PySide6 6.11 抛 AttributeError(应为 `QPalette.ColorRole.Base` 类级访问); 首帧绘制时才炸, 表象是 `win.show()` 处 access violation(faulthandler 定位), offscreen 自测抓不到——**windows 平台 GUI 冒烟不可省**; 自定义 paintEvent 必须 try/finally `p.end()` |
## 6. 镜像与外部资源
- pico-sdk: `D:\toolchain\pico-sdk`(2.3.1, 浅克隆), tinyusb 锁定 `86ad6e56`
(0.18.0, 来自 gitee.com/mirrors/tinyusb)
- Arm GNU 13.3 / CMake 3.31 / Ninja: `D:\toolchain\*`(PATH 已有 11.3, 13.3 需全路径)
- zig(宿主编译 pioasm 用): `pip install ziglang`, exe 在
`D:\toolchain\zig\ziglang\zig.exe`(pip -t 平铺安装时注意真实路径在包目录下)
- 本仓代理前缀: `https://ghproxy.net/https://github.com/...`(git clone 可用)