docs/zh/plans/render-pipeline-threads.md M4: the thread pipeline now
keeps its decode thread ahead of the render thread and the app's
playback window consumes in-process frames.
- Render queue: priority-ordered by JobSchedule.priority (Seek >
Playback > Background, FIFO within a class), so interactive frames
jump playback exports/autocache. Seek posts may over-admit the bound:
priority only reorders queued jobs, so a full queue of background work
must not park the UI thread until an export frame finishes.
- Decode queue: rendezvous Requests are served ahead of queued
Prefetches (a frame the renderer needs never waits behind speculative
decodes); Sync barriers stay FIFO. The queue is a bounded
Mutex+Condvar structure, preserving the request backpressure and the
wait_idle contract.
- Playback read-ahead: a Playback job's footage decode requests are
derived from its montage/footage spec on post (same media time, size
and force_format.unwrap_or(F32) as the eval) and queued immediately,
so frame N+1 decodes while frame N runs its GPU passes.
- App window: PreviewWindow slots are generalized to
PreviewSlot::{Shm, Video}; the pipeline's in-process TicketPayload is
cached and consumed by cpu_frame exactly like a worker slot.
PipelineBackend::preview_window_capacity reports the render-queue
headroom, so playback posts are capped to what the queue can take;
cancel_preview_frame drops queued frames the playhead has passed,
matched on the full (sequence, frame, version) key so one monitor's
window never drops the other sequence's same-numbered frame.
- Tests: decode-queue preemption/FIFO, render-queue ordering, request
derivation, and deterministic end-to-end M4 tests: a prefetch that
must be reused by the render request (LRU hit, single decode — the
read-ahead claim is falsifiable), a parked-render-thread priority test
where a full queue of background work still lets a Seek over-admit and
run first, and a sequence-aware cancel test. The playback prefetch
smoke asserts prefetches == distinct decodes == frames; it does not
claim zero heap copies (Frame.data is deep-copied at the eval-cache
and service-LRU boundaries today).
- bench_playback gains a pipeline mode with CPU (self+children) and
first-frame latency; both backends now produce F32 frames so the
comparison is like-for-like. The §3.4 backfill records the numbers:
at the proxy size the pipeline is faster with a lower first frame; at
1080p peak throughput is below the multi-worker pool, but that is an
artifact of the decode still being CPU software (M5), not a case for
pooling decode threads — GPU decode is a single device/queue and the
zero-copy import shares one GPU memory pool, so the single decode
thread stays the target shape.
长期计划(plans)
本目录收纳 Oak 的中长期规划文档与并行执行计划。已完成的战役
文档归档在 completed/;进行中的计划在下方目录。
目录
| 文档 | 内容 | 启动前提 |
|---|---|---|
ai-agent-design.md |
AI Agent 插件设计(已按 OPP/1 重写):多模态 LLM 作为外部插件经策展工具面自动剪辑,render.* 取帧回喂形成"编辑→看图→再编辑"视觉闭环;事务化编辑、双层确认、声明式 AI 面板、Mock LLM/回放夹具测试、A1–A5 里程碑 |
external-plugin-system P1–P3 完成(面板需 P4) |
external-plugin-system.md |
外部功能插件系统:插件=独立进程(非库加载),JSON-RPC over stdio 控制面 + shm 数据面(泛化 M15 render-worker 传输);策展宿主 API(事务化可撤销编辑、取帧回喂 AI)、声明式/像素面双 UI 路径、能力位与确认模式;含与 ai-agent-design.md 的关系与 P1–P6 里程碑 | 已解锁(RIIR + M15 完成),随时启动 |
external-plugin-protocol.md |
插件协议规范 OPP/1:NDJSON 分帧 + JSON-RPC 2.0 双向信封、握手/心跳/关闭、全量方法/事件/错误码、编辑事务协议、shm 数据面(无头部无锁)、声明式与像素面 UI 协议、限流配额、版本演进规则、AI 粗剪报文示例 | 随 external-plugin-system 启动 |
render-pipeline-threads.md |
渲染管线改造:单解码线程 + 单渲染线程 + 主进程上屏(GPU 单队列,多进程无意义);解码硬解优先且零拷贝(FFmpeg hwaccel 经 DMA-BUF/DXGI/IOSurface/CUDA 导入,CPU 解码上传仅 fallback,手写 GPU 解码为次选);OpenFX 收编进唯一隔离进程;decode→render→present 三队列流水线;内置效果全 GPU 零拷贝;resolve 重写为 match+Job 单循环并升级为 Job 图(GraphInput/GraphOutput 虚拟端点可见、禁删,从输入节点 Kahn 形态 BFS 至全部分支汇聚输出节点);M0a–M5 里程碑 | 已解锁,随时启动(M0a 独立先行) |
其他参考
- 构建:
docs/zh/build.md、docs/zh/build_macos-zh.md - 工程文件:
docs/zh/project-file-reference.md - 代码风格与 Google Test 要求:
CONTRIBUTING.md(仓库根)