From 0d747da4704951e12f87df71e5d6280e73dccb5b Mon Sep 17 00:00:00 2001 From: Swung0x48 Date: Fri, 18 Sep 2026 21:35:08 -0400 Subject: [PATCH] [Docs] (Disaggregated): ROADMAP's P5e row had only its status cell updated; the other three were still the pre-phase plan The previous commit changed the status cell to "twelve packages landed, run-ahead armed" and left the scope and exit-gate cells saying eight packages, 19 rulings, "the integration commit flips kMGPipeP5eRunAheadReady", and an exit gate drafted BEFORE the phase started - several of whose items later proved unexecutable as written. All three cells are rewritten: - Scope cell: twelve packages in three waves (including fix1 / pa / mv / gl / ra2), rulings ID-80..136, both constants flipped. It also names the largest migration (the per-draw GetProgramForDraw) as having changed NO wire structure at all - the record already carried the per-link ProgramArchive, and what was missing was a reader that still asked the frontend object. Links to P5E-RUNAHEAD.md. - Exit-gate cell: rewritten into what was actually measured (unit 2256, integration-split 179/179, integration-gpu 1357/1357, three flavours with each arm asserting its EFFECTIVE compile define, strict hard green with zero Fatal, the device at VD32 level with monolith and +69% p50 against lockstep), plus what has not been executed (the three negative controls, the per-package red-once reruns, E1's control failing its own self-check, G1 still asserted by CI), plus the criteria that are now VOID (rsp = 0 is empty by construction, rewritten by ID-119; VERB_BARRIER=0 may not serve as the paired control, ID-114, because it also disarms run-ahead). - Debt table, rsp row: P5e rewrote what that number means. It now reads as the hard-green lane plus eight Admitted rows, and says why the original criterion was empty - CountBarrierPull's unbarriered arm sits before ++g_residualPulls and is [[noreturn]]. - Debt table, unmigrated row: client vertex arrays are a named refusal under run-ahead (ID-82) and have their own expected-red lane, integration-clientarrays-split (ID-134); staging stays P8's. - Open question 18 added: the two sides of split are unbalanced (at VD32, apply 11-12 ms against client 15.7 ms, with the client ~94% saturated). Moving work from client to apply lowers the bottleneck directly - meaningless under lockstep, where the two add serially, and a lever only because of run-ahead. It needs a fresh profile first: with the wait gone, every tail item's denominator has changed. - The header status line gains the P5E-RUNAHEAD.md link. Doc citation check: seven files under docs/Disaggregated, 58 citations, 0 problems. --- docs/Disaggregated/ROADMAP.md | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/docs/Disaggregated/ROADMAP.md b/docs/Disaggregated/ROADMAP.md index 32313b67..97d818d9 100644 --- a/docs/Disaggregated/ROADMAP.md +++ b/docs/Disaggregated/ROADMAP.md @@ -1,6 +1,6 @@ # MGPipe 路线图 -> 状态:**P0、P0.5、P1、P2、P3a、P4a、P5、P5b、P5c、P5d 已收官**(P5c:2026-09-17,代码头 `b88e8487`;P5d:三轮,2026-09-18,代码头 `1f8de61b`)。当前头、逐门数字、开放项与下一步见 **[`CURRENT_STAGE_PROGRESS.md`](CURRENT_STAGE_PROGRESS.md)**;设计见 `ARCHITECTURE.md`;逐阶段实测见 `MEASUREMENTS.md`;P5d 报告见 [`P5D-INPROC-PERFORMANCE.md`](P5D-INPROC-PERFORMANCE.md)。**当前在 P5e**(退役 Espryt draw path 的 lockstep,契约 `MobileGL/MG_Remote/CONTRACT-P5E.md`;十二包已全部落地合并,**run-ahead 已武装**,头 `25fba0d5`;strict 车道硬绿 179/179、`integration-gpu` 1357/1357、三个构建 flavour 全绿;设备上 inproc 已与 monolith 齐平,见 `CURRENT_STAGE_PROGRESS.md` §2.6 与 `MEASUREMENTS.md` §11);之后才是 P6 spawn transport(此时只是传输替换)。 +> 状态:**P0、P0.5、P1、P2、P3a、P4a、P5、P5b、P5c、P5d 已收官**(P5c:2026-09-17,代码头 `b88e8487`;P5d:三轮,2026-09-18,代码头 `1f8de61b`)。当前头、逐门数字、开放项与下一步见 **[`CURRENT_STAGE_PROGRESS.md`](CURRENT_STAGE_PROGRESS.md)**;设计见 `ARCHITECTURE.md`;逐阶段实测见 `MEASUREMENTS.md`;P5d 报告见 [`P5D-INPROC-PERFORMANCE.md`](P5D-INPROC-PERFORMANCE.md),P5e 报告见 [`P5E-RUNAHEAD.md`](P5E-RUNAHEAD.md)。**当前在 P5e**(退役 Espryt draw path 的 lockstep,契约 `MobileGL/MG_Remote/CONTRACT-P5E.md`;十二包已全部落地合并,**run-ahead 已武装**,头 `25fba0d5`;strict 车道硬绿 179/179、`integration-gpu` 1357/1357、三个构建 flavour 全绿;设备上 inproc 已与 monolith 齐平,见 `CURRENT_STAGE_PROGRESS.md` §2.6 与 `MEASUREMENTS.md` §11);之后才是 P6 spawn transport(此时只是传输替换)。 ## 通用纪律(每个 commit) @@ -28,7 +28,7 @@ | **P5b** `inproc` verb migration | ✅ `37fc4fdb..82683d4a` | class-C 普查决定顺序;d1 19 / i1 7 / t2 6 / f1 11 槽迁移;sync 五槽;具名 blit;GLES mip descriptor;r1 / r2;收官审查三项修复。发射表 A=2 / B=54 / C=15 | 主机全门 `348d22a4` complete;`integration-split` 107/107;合并普查零回退、79 trace 72/6/1;**Redmi 正确性 8/8 + 四臂 A/B、barrier tax 首测**。§7 | | **P5c** `inproc` 共享内存读点归零 | ✅ `11ac3de6..b88e8487` | server 端纹理 staged shadow(`StagedTextureStore`,句柄为键、整段覆盖、defined-ness 追踪);`SEG_EVENT` 三个 producer + `kEventGlError`(反向通道零裸指针);sink / twin 按记录句柄解析(blit 具名臂经 verb 句柄工作区,Magma 走 G6 消费臂);`applier_reset` / `object_death` 控制记录(opcode 77/78,framebuffer 首个 wire delete);`set_context_values`(79)退役全部值类 BARRIER-PULLED 行,三 shutter 自答;双层 `Fatal{RoleViolation}` 守卫 + `InBarrierWait` 接线;两个具名豁免 scope(通告家族 P4b/P7、G6 registry 家族 P3b/P4b)承接未到期的债 | 角色守卫开启下 unit 2187/2187(strict 下同绿)、`integration-split` 111/111、每层守卫 red-once 按名变红;纹理 `0xDD` audit 在 bsl / complementary 两条 in-world trace 零 Fatal;rsp 按帧实测(bsl 948.5/帧,残留全为钉住的对象类 15 行);G1 三个认定 resize(SwapchainObject::Create / CopyTexSubImage2D / ScopedRestartIndexSubstitution,均已具名)+ `.text` −16 B、pull 构建零 MG_Remote 符号;G5 保护区字节一致;双生成器 --check/--self-test 绿 | P5b | | **P5d** `inproc` 性能专项 | ✅ `cb06538c`、`56a77348`、`1f8de61b` | 一二轮:persistent-map 推送三级臂(mprotect 脏页追踪 + 哈希抑制 + 绑定过滤 `PushDrawConsumers`)、barrier 批处理 `MOBILEGL_IPC_BATCH_WAITS` + 延期销毁队列、自旋时钟 64 合 1、零页注册 + shadow 页对齐分配。三轮(按符号化 profile 逐项切,四包 + 一份 lockstep 可行性研究):apply 空转轮询零锁(控制邮箱原子影子位)、`Doorbell::Wait` 校准自旋稳态不读时钟、wait/park 计数进 stats;`OnApplyThread()` 内联为线程指针比较、三个 scope 深度计数器退掉 `thread_local`;shadow 分配尺寸补页、追踪范围向外对齐、边块哈希消失、脏页排空修复;image unit 高水位、残余填充 memo、server stamp 常量表;`generate_mipmap` 不再免等(apply 读残余输入)、death 测试围栏 | 三轮设备(Redmi,CPU 定频):inproc **64.3 → 103-106 fps**(p50),client 线程 CPU 15.0 → 9.2 ms/帧、apply 12.4 → 7.0-7.4;monolith 同场景 115(120 Hz vsync 封顶的运行)/ 206(一次未封顶,渲染线程 5.0 ms/帧 大核);配对比较以逐线程 CPU/帧为主,见报告"数字"节;unit 2203/2203、`integration-split` 111/111(两条曾 flaky 的用例复跑 6/6);双生成器、include 闭包、dirty-surface、doc 引用绿。未完成:R-1 序列化(研究结论:留给 P3b/P4b 后的 P11 `gPipeInputs` 版本化)、线程放置(内核忽略亲和)、`SetHashSuppressor` 哈希等小项。报告:[`P5D-INPROC-PERFORMANCE.md`](P5D-INPROC-PERFORMANCE.md) | P5b | -| **P5e** 退役 Espryt draw path 的 lockstep | 🚧 进行中(十二包全落地,**run-ahead 已武装**,头 `25fba0d5`) | 契约 `MG_Remote/CONTRACT-P5E.md`(规则 F:未设障记录的 apply 不得读任何 client 内存;19 条裁定见 §9)。八包:**c0e** 契约 + 线上行(`PipeCalls.def` 第五列 `WaitClass` + `MGPipeWaitClassFor`、`set_program_bindings` opcode 80 空路由、`kCapRunAheadApply` 位 10、`kDrawClientArrays`、子系统位 13、`MGPipeImageAccess` 一张表、两个旋钮、跨包 seam 声明)→ **id** 身份(registry 按 `{slot, gen}` 重键、by-handle resolver、分配器守卫)→ **vi / sb / pg / tx2 / fb** 五个 per-draw 家族并行(VAO / 缓冲绑定点 / program 归档 + 绑定 / 纹理 + sampler 窗口 / FBO + image)∥ **ra** 传输机制(等待规则 `EmitAndWaitTails`、present credit、`gPipeInputs` 变 server 角色内存、事件环流控)。集成 commit 翻 `kMGPipeP5eRunAheadReady` | 集成门(§3):unit 两臂绿;`integration-split` 111+ 绿 + inproc 普查零回退 + 79 trace 无新首阻塞;`integration-split-strict` 转**硬绿车道**(只允许 §7 白名单的 `[BARRIER-PULLED]` 标记,未设障记录 `rsp` = 0);三条阴性对照(`MOBILEGL_IPC_RUN_AHEAD=0` SSIM 一致、`VERB_BARRIER=0` 在设障行变红、Magma 上 `RUN_AHEAD=1` 记一条日志后跑 lockstep);每包 red-once 在集成树复跑;G1 0/0/0/0、G2、G14、G5;monolith push 四条 A/B trace SSIM 不变。设备出口(§4,Redmi 30 s 在世界窗口,四臂):fps ≥ lockstep、client 线程 CPU ms/帧 < lockstep、SSIM 不变,且逐 op 等待清单里**没有 `kWaitApplied` 行、没有逐 draw 的 reply 行** | P5d | +| **P5e** 退役 Espryt draw path 的 lockstep | 🚧 进行中(十二包全落地,**run-ahead 已武装**,头 `25fba0d5`) | 契约 `MG_Remote/CONTRACT-P5E.md`(规则 F:**未设障**记录的 apply 不得读任何 client 内存;ID-84 限定它只约束未设障记录);裁定 **ID-80..136**(`~/w7/notes/p5e/INTEGRATOR-DECISIONS-P5E.md`)。**十二个包,三波**:wave 1 **c0e**(契约 + 线上行:`PipeCalls.def` 第五列 `WaitClass`、`set_program_bindings` opcode 80、`kCapRunAheadApply` 位 10 仅 DirectGLES 臂、`kDrawClientArrays`、子系统位 13、两个旋钮)→ **id**(registry 按 `{slot, gen}` 重键、by-handle resolver、分配器守卫);wave 2 **vi / sb / pg / tx2 / fb** 五个 per-draw 家族 ∥ **ra**(等待规则、present credit、`gPipeInputs` 变 server 角色内存),加 **fix1**(设备发现的 monolith 臂回归,ID-107);wave 3 **pa**(program 家族离开前端)、**mv**(multi-draw + 五个档位的门禁条目)、**gl**(门禁机制本身 + 两处潜伏崩溃)、**ra2**(翻开关后暴露的竞态)。**`kMGPipeP5eRunAheadReady` 与 `kMGPipeP5eClientWaitRuleLanded` 均已翻**。最大的那次迁移(逐 draw 的 `GetProgramForDraw`)**没有改动任何线上结构**:记录早就带着逐 link 的 `ProgramArchive`,缺的是仍去问前端对象的读者。报告 [`P5E-RUNAHEAD.md`](P5E-RUNAHEAD.md) | **已达成**(头 `25fba0d5`,run-ahead 已武装):`unit` 2256/2256;`integration-split` **179/179**;`integration-gpu` **1357/1357**(ID-109 新增的常设步,覆盖 push 构建的**第二条运行时臂**);`flavours` rc=0(ID-124:pull / push / split 三个,且每臂**断言生效的编译宏**而不看 flag);`integration-split-strict` **硬绿**——逐条普查 179/179、`Fatal{` 为零、`Admitted{` 恰为八行,白名单**生成**而非手抄(ID-116/125/128 的三个析取项)、车道是**两侧棘轮**;两条预期红车道各自具名断言。设备(Redmi,CPU 定频且回读验证,臂交错):**VD32(~3550 draws/帧,两臂都远离上限)inproc 与 monolith 齐平**(p50 中位 59.9 vs 58.5,client CPU 15.72 vs 16.19 ms/帧,每臂五次),相对它取代的 lockstep **p50 +69%**。**尚未执行**:§3 item 4 的三条阴性对照、item 5 的逐包 red-once 重跑(其证据形式当时**不可执行**,ID-121 已重排到车道变绿之后);`split_negative_controls.sh` 的 E1 对照自检就失败且所索 Fatal 在默认配置下不可能触发(ID-122);G1 仍由 CI 断言(ID-123);契约 §3.2(per-role stamp 存储)与 §8 修正 8 标为 UNLANDED。**已作废的判据**:原定的“`rsp` = 0”按构造就是空的(ID-119 改写);“四臂设备出口”中的 `VERB_BARRIER=0` 不得做配对对照(ID-114,它会顺手关掉 run-ahead) | P5d | | **P6** spawn transport | P5e 之后 | `SocketTransport`(socketpair + fork/execve,envp 剔除 + 强制 monolith 双保险);`ServerMain`;`MOBILEGL_IPC_SERVER_PATH` + `dladdr` 兜底;有界重试握手;EOF 即时退出;device-lost latch;EGL forwarder 的控制面帧;P5c 留下的 `s_synced` / `g_syncedRenderStateParameters` 按 context 世代重置 | P5b 的完整渲染路径在 `spawn` 下绿;进程树只多一个子进程;`HeadlessGL` fork 预检无孤儿;OpenRA 在 Adreno 830 上 split SSIM ≥ 0.99 | | **P3b / P4b** 深化(Espryt) | 待排 | 按存储属主键控的发射游标与 view 索引重映射;`g_fboTextureSyncList`;`ResolvedTextureBindingMemo` / `SamplerPassMemo` / image sweep / program registry 重键;XFB scatter 搬到 client;删 fragColor 重推导 workaround 与 `g_broadcastMemo*`;raw-depth-fetch sampler 原生化;回读 / pack state;P4a 记下的 R-3 / R-4 / R-5 / R-7 / R-10 / R-11;`ProgramArtifacts.h` 的 NDK 尺寸钉 | 纹理 / program 场景;CTS `texture_*` / `shader_image_*` / `packed_pixels` 在 0.5 pp 内;每一个 Iris trace;`TextureUploadShapeScenario` 升级成门 | | **P7** DirectVulkan(Magma)全量迁移 | 待排 | 其余 10 个子系统:`SetupDrawSnapshot` 探测字段塌成 dirty mask;占位纹理原生化;具名 UBO host payload(D-B8);内部 shader 烘焙;`VertexInputStateFactory` 内容寻址 CSO;D18 容器纪律保留 | 集成 + trace 在 Magma 的 push 与 split 下全绿;verify 零分歧;`nm -D libMobileGLServer.so \| grep glslang` 为空;CTS 0.5 pp 内。**再基线检查点:中点完成子系统 < 40% 立即重定基线** | @@ -116,14 +116,14 @@ CTS 周转单独计价(`gl44to46` 约 56,271 例):逐阶段只跑该阶段 | 债务 | 去向 / 当前口径 | |---|---| | P5 的 27 个普通 inproc wrong-answer(历史计数) | 22(14 layered + 3 packed depth/stencil + 5 framebuffer recycle)→ P4b/P7 texture readback;3 → P7 query;1 inspection → P6;1 FBO/RBO delete 用例在 r1 定向验证中通过,完整像素因果未隔离。最终计数以 `MEASUREMENTS.md` §7.2 的同名比对为准 | -| `rsp` residual inputs | STRICT_ERRORS reduced lane 19 abort / 2 skip;`rsp=35` 只是有 stamp 读点的下界,无 verb stamp 的 sticky / non-verb forward 仍可绕过计数;P7/P8 补逐字段归类,其余按字段的 P3b/P4b/P7 退役 | +| `rsp` residual inputs | **P5e 已重写这条的口径**:`integration-split-strict` 现为硬绿车道(逐条普查 179/179、`Fatal{` 为零、`Admitted{` 八行,均有退役相)。原先的“未设障记录 `rsp` = 0”**按构造就是空的**:`CountBarrierPull` 的未设障臂在 `++g_residualPulls` 之前且 `[[noreturn]]`,所以 `rsp` 只数**设障**的 pull;ID-119 改写为“`rsp` 只数被采纳的设障 pull,且等于被采纳标记的计数”。剩余八行分属 P7 / P8 / P9 / P3b•P4b | | `SEG_REPLY` 2 MiB 单槽 payload cap | 更大 readback 需要 P6+ chunking 或专用 carrier(ID-47) | | `GetCaps` 的两个 blobref | 目前不骑 record;一旦运输,必须有 server→client carrier rule,不能套 `SEG_STAGE` | | PACK-PBO readback | P5 具名拒绝;真实形状是 server 写 buffer resource、client `MarkGpuWritten`,P6(ID-57) | | ABI fingerprint | 不混 segment sizes;改变 8/32/16 MiB + 256 KiB ledger 时仍欠这项 | | 默认 32 MiB staging | 目标负载单次 128 MiB 上传装不进默认 stage;普查 / Redmi 显式 256 MiB profile,默认不改;分块 / 专用 carrier 归 P8(开放问题 11) | | P5b 的 inproc 依赖 | 具名 blit 的 scoped client binding + barrier;mip descriptor 的 registry 身份查询依赖 barrier-held object;FBO death 的 inproc mailbox。P6 必须替换 | -| 未迁移与仿真路径 | 15 个 class-C 槽(query / sync 尾 / `GetTexImage` / `SetSwapInterval`)→ P9 / P10;client vertex arrays、multi-draw client indices、RGB 三通道 CPU mip、renderbuffer copy endpoint、未绑定 named clear、`texture-remint-pull` 仿真保留具名拒绝 → P8 / P9;Magma split compute / image 路径 82 个错答 → P7 | +| 未迁移与仿真路径 | 15 个 class-C 槽(query / sync 尾 / `GetTexImage` / `SetSwapInterval`)→ P9 / P10;client vertex arrays、multi-draw client indices、RGB 三通道 CPU mip、renderbuffer copy endpoint、未绑定 named clear、`texture-remint-pull` 仿真保留具名拒绝 → P8 / P9;Magma split compute / image 路径 82 个错答 → P7 | **P5e 补**:client vertex arrays 在 run-ahead 下是**具名拒绝**(ID-82,`Fatal{UnmigratedVerb, "DrawArrays+CLIENT_ARRAYS"}`),并有自己的预期红车道 `integration-clientarrays-split`(ID-134);staging 仍归 P8 | E2 wire 内容控制 | draw-drop 是 OpenRA 的有效控制(758 draws,SSIM 0.000036);clear-drop 被全屏 overdraw 掩盖,不能作控制 | | max record bytes | 实测 reduced / OpenRA `maxrec=784 B`,默认 cap 4 MiB;只代表所测负载,后续索引 / indirect 尾仍须记录 | | 树外脚本 | 普查跑器、`wsl_p5_gate.sh`、Redmi 定频行都在 `~/w7/notes/`,git merge 不会传播 | @@ -150,3 +150,4 @@ P0 已回答的不再列出(spike A 的域、spike B 的分档、`posix_spawn` 15. **monolith 的 `*IndirectCount` 不调 `SyncGpuWrites()` 是不是潜在缺口。** 独立 `dev` 问题,拆分不得借机顺手修。 16. **索引宿主镜像的实际内存占用。** MC / Sodium / Iris 语料里 element-array buffer 总量未测;若显著超 64 MiB,退化路径的频率与代价必须实测。P8。 17. **`create-indirect` fixture 在 Adreno 830 上的失败**是 `dev@81b17c0b` 就有的(基线 APK 复现),不是本分支造成;`rd12` + Magma 在两台 Adreno 830 上的 `scudo::reportMapError` 崩溃同样是 `dev` 侧。两者排除在设备 A/B 之外、留在桌面语料里;P8 要在 `create-indirect` 上断言 `roundtrips-per-frame == 0`,所以 `dev` 的修复在别人的关键路径上。 +18. **split 两侧的负载平衡。** P5e 解锁出来的新问题:VD32(~3550 draws/帧)下 apply 线程 **11-12 ms**、client **15.7 ms**,**client 是瓶颈且打满 ~94%**。把工作从 client 挪到 apply 会直接降瓶颈——这在 lockstep 下毫无意义(两侧串行相加),**run-ahead 才使它成为一个杠杆**。供选:编码侧的 emitter、tracker 走查、持久映射的脏页追踪(`change_protection` 在侧写里占 1.3%)。需先重新侧写:等待消失后尾部各项的分母都变了。排在 P5e 之后