Files
MapLibreParticleLab/docs/报告/STEP-097_A2_阶段验证记录_v3.md
tei b1239ac3b1
Some checks failed
validate-scripts / validate-scripts (push) Has been cancelled
docs(step097): close A2 Android Core validation
2026-09-26 15:18:45 +09:00

9.8 KiB
Raw Permalink Blame History

STEP-097 A2 阶段验证记录 v3

1. 结论

A2 Android/Core 验证完成;STEP-097 整体仍 PARTIAL。 A2 的 04–07 在 Core、OpenGL/Metal host 回归和 FZG1-2 设备闭环达到本阶段检查点。没有开始 B/C,没有执行 Jest、STEP-098 或 .13 发布。iOS runtime 依用户决定豁免,记为 USER_ACCEPTED_WITHOUT_IOS_RUNTIME_TEST,不是 iOS PASS。

Codex 会话配置:GPT-6 Luna High,用户可见会话。RDC 独立执行了 CMake/GTest、shader generator、标准 Android APK 构建、FZG1-2 安装和设备场景。Codex 本轮未执行这些命令。

2. Git 与版本基线

  • 仓库:Mac Mac-mini-tei.lan,/Users/tei/dev/MapLibreParticleLab;分支 particle/main。
  • 验证源码基线 HEAD:5bb1a0e6353c5dfe8db8a61bbeba9cef447280ef;A2 源码工作树 dirty,尚未提交。结束 HEAD 未变化。
  • 本次记录前的 A2 source diff SHA-256:18927a5f30a88f5c1c3a00e0017473dc33b04151c227e4baf52250dc4ad2e6a2;与 artifacts/maplibre-particle/step097-a2-final-validation/mix-reuse-build-source.diff SHA-256 完全一致。标准 APK 的 build-info 也记录相同 commit/branch 和 git_dirty=true,证明设备验证所用 source snapshot 与本轮代码一致。
  • Integration main:318f8ccf911ac3136c3086a1d14e61f83e2d4bce;C-001 未修改。
  • 冻结的 .13 发布坐标、tag、manifest 与产物未修改;本轮不发布。
  • 用户 untracked docs/40_任务/STEP-098_QBIN_V4单帧首显与八帧滚动缓存_Codex任务_v1.md 保持原样、未 stage。

3. A2 实施内容

项 实施与不变量
04 N04/B06 Forecast PLAY Map Continuous update 驱动 Source-owned monotonic forecast clock;Android/iOS timer 只负责唤醒。同步 SourceObserver reentry 由 forecastTickInProgress 防止重复推进。显式 setTime、PLAY/PAUSE、rate、clear 保持 Core clock 所有权。
05 B13 GPU endpoint / mix-only reuse sameFieldGpuContent() 继续只表示 version-agnostic decoded payload 等价;新的 sameFieldGpuEndpoint() 严格比较 revision/time、U/V、validity、grid、encoding 等 renderer endpoint 身份。Source 对相同 content identity、binding、immutable decoded frame 与 plane/validity storage pointer 复用已有 materialized T0/T1,只更新 sampleState。frame/revision 或任一输入 storage 改变则重新物化;invalid/clear fail-closed。移除每 tick 深比较完整 snapshot vectors。
06 B07 RGBA8 signed zero 增加内部 particle_gpu_math.hpp signed RGBA8 编码,byte 128 明确表示 0;shader 以 high precision 还原 byte。未改公开 QBIN/FieldProfile encoding。数学测试覆盖正负取消、零、NaN/invalid 与量化下限。
07 B08 Mercator U/V helper 与 GL/Metal shader 的东向 U、北向 V 都使用相同纬度度量,极区分母夹紧;保持 canonical m/s 和现有视觉时间倍率。测试覆盖 0°/45°/60° 四方向及极区有限值。

三项 A2 Source 测试还覆盖 50 次 mix-only clock tick 不重物化、真实 endpoint 和相同 valid-time revision 替换触发重物化、clear 后 projection 清空,以及 source notification 嵌套 tick 不双推进。Host-facing 新 API、C-001、QBIN 格式未改变。

4. 修改文件

源码、shader 与 A2 测试

  • include/mbgl/particle/field/field_data_adapter.hpp
  • include/mbgl/particle/field/particle_gpu_math.hpp(新增)
  • include/mbgl/shaders/gl/particle_gpu_validation.hpp
  • include/mbgl/shaders/mtl/particle_gpu_validation.hpp
  • include/mbgl/style/sources/raster_array_source.hpp
  • platform/android/MapLibreAndroid/src/main/java/org/maplibre/android/maps/WeatherRuntime.java
  • platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/particle/ParticleCoreLayerValidationActivity.kt
  • platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/particle/Step097V4GoldenFixture.kt(新增)
  • platform/android/MapLibreAndroidTestApp/src/main/assets/integration/step097-v4/wind/T0.qbin、T1.qbin、contract.json(新增 test-only fixture)
  • platform/ios/src/MLNParticleFieldRuntime.mm
  • shaders/particle_gpu_validation.fragment.glsl、shaders/particle_gpu_validation.vertex.glsl
  • src/mbgl/map/map_impl.cpp
  • src/mbgl/particle/field/field_data_adapter.cpp
  • src/mbgl/particle/field/field_projection_materialization.cpp
  • src/mbgl/particle/field/field_runtime.cpp
  • src/mbgl/renderer/layers/render_particle_validation_layer.cpp
  • src/mbgl/style/sources/raster_array_source.cpp、src/mbgl/style/sources/raster_array_source_impl.hpp
  • test/CMakeLists.txt
  • test/particle/field_runtime.test.cpp
  • test/particle/particle_gpu_math.test.cpp(新增)
  • test/source/raster_array_v4_host_api.test.cpp
  • test/style/source.test.cpp(仅修正旧断言对 sameFieldGpuContent() 的预期;严格 endpoint identity 由新断言覆盖)

本报告之后的文档变更为 docs/30_设计/STEP-097_V13三轮问题去重与修复矩阵_v1.md、本报告、docs/报告/STEP-097_V13三轮审查问题合并修复_Codex完成报告_v2.md、docs/50_Step记录/STEP-097_V13三轮审查问题合并修复_v1.md、docs/60_测试/STEP-097_V13修复后集中验证清单_v1.md 及根目录 粒子开发记录.md。无其他步骤范围代码。

5. RDC 构建与测试

验证 RDC 结果
原有完整 58 项回归(修正旧断言后) OpenGL 58/58 PASS。先前 57/58 的失败根因是旧断言把 sameFieldGpuContent() 当成 revision-sensitive;函数原有契约明确忽略 generation/dataVersion。测试现在分别验证 payload 等价与 strict endpoint identity,没有放宽 endpoint 比较。
当前 broad Core filter Particle*.*:Source.RasterArray*:Source.HostField*:Source.ParticleField*:Source.CanonicalField* OpenGL 121/121 PASS;Metal host 121/121 PASS。
A2 定向 Source 三项 OpenGL 3/3 PASS;Metal host 3/3 PASS,包括 mix-only 50 ticks、endpoint/revision invalidation 与同步通知重入。
shader generator node shaders/generate_shader_code.mjs 连续两次成功,输出幂等。

构建/测试日志:artifacts/maplibre-particle/step097-a2-final-validation/mix-reuse-broad-opengl.log、mix-reuse-broad-metal-host.log、mix-reuse-focused-opengl.log、mix-reuse-focused-metal-host.log、build-mix-reuse-opengl.log、build-mix-reuse-metal-host.log。Metal host 测试是 Mac Core runner,不是 iOS runtime 或设备 Metal 验证。

6. Android APK 与 FZG1-2

  • 标准命令由 RDC 执行:./tools/particle_android_validation/build_validation_apk.sh。
  • 产物:artifacts/maplibre-particle/android-validation/MapLibreAndroidTestApp-validation-opengl-debug-x86_64.apk;OpenGL Debug、x86_64、61,753,803 bytes;SHA-256 27bf4a6cc191bd86c4d1c10398478d81c2999edd61fe7242e40e5188516b0ca5。步骤归档副本:artifacts/maplibre-particle/step097-a2-final-validation/MapLibreAndroidTestApp-A2-mix-reuse-x86_64.apk。
  • RDC 安装至 Panasonic FZG1-2(ADB 192.168.200.139:5555)成功;设备内 APK SHA-256 与构建产物相同。
  • Test-App-only Golden Wind T0/T1 场景脚本 exit 0,17 PNG、24 steps、ANR=0:load、seek 25/75、speed 2x/1x、PLAY 30 秒与 PLAY 时 UI/TIME 响应、PAUSE/stable pause、replay、CLEAR、reload、再次 PLAY/PAUSE。截图 after-v4-mix-reuse/05_play_15s.png 可见粒子。
  • 上传/reset 计数按资源 epoch 记录:clear/reload 前 mix-only playback 稳定于 fieldUploadCount=6/resetCount=2;CLEAR/reload 后计数合法增加到 fieldUploadCount=10/resetCount=4,reload 后 playback 稳定。没有宣称跨 CLEAR/reload 零上传/零 reset。
  • APK 输入源码 diff 与保存快照 mix-reuse-build-source.diff 的 SHA-256 都为 18927a5f30a88f5c1c3a00e0017473dc33b04151c227e4baf52250dc4ad2e6a2。

7. 历史失败、性能与平台边界

  • 2026-09-26 12:43 首次 FZG1 ANR 的 main stack 是 Forecast clock tick 的同步 SourceObserver reentry;forecastTickInProgress guard 与回归测试针对该缺陷。后续有一轮没有 ANR 但 UI/TIME 仍不可用、主线程高负载;debuggerd 定位到每 tick 对大 QBIN projection 重复物化 validity/vector 并深比较 snapshot。mix-only immutable snapshot reuse 后,最终 FZG1 闭环通过。
  • 历史 debuggerd、首次 ANR、第二次无响应试跑及最终验证证据均保存在 artifacts/maplibre-particle/step097-a2-final-validation/;报告保留失败经过,不把中间失败覆盖成 PASS。
  • PLAY 30 秒只是交互闭环,不是 long-run 稳定性、FPS、frame time、内存或 GPU 性能基准;本轮没有这类数字。
  • 用户豁免 iOS runtime:USER_ACCEPTED_WITHOUT_IOS_RUNTIME_TEST。Android 与 Metal host Core 结果不能替代 iOS device PASS。
  • Integration C-001 未改,Host 公开 API/QBIN schema 未改;没有进入 B/C、没有运行 STEP-098/Jest、没有更改 .13 发布物。

8. 阶段与 Git 收尾

  • A2 状态:Android/Core 代码、原生回归和 FZG1 验证完成。
  • STEP-097 整体:PARTIAL;B/C 未开始。其余 24 项逐项状态见更新后的去重矩阵。
  • 本报告无 commit/push。RDC 后续做独立 QA 与 scoped Git 操作;用户未跟踪 STEP-098 不得纳入。

9. RDC Git 源码提交核验(报告编写后更新)

  • A2 源码、标准 TestApp 内部 fixture 与定向测试已以 f49ffa68a17e0a505199bdbeccf07f8543f3a05f 独立 scoped commit 提交并推送 origin/particle/main;26 个代码/fixture/test 路径,未包含任何文档、STEP-098、Integration、NavSea 或发布资产。远端 HEAD 回读相同。
  • 该提交只是把已经通过 RDC 验证的源码固定进 Git;构建时仍如实为 5bb1a0e + dirty source diff。源码部分保存快照的 SHA-256 对应提交内容,不把后续文档更新误算进构建输入。
  • 文档与 Step/矩阵/测试清单将作为独立 scoped commit 收尾。