Skip to content

fix(vdd): share producer probe for direct capture#736

Open
qiin2333 wants to merge 2 commits into
masterfrom
codex/vdd-producer-probe
Open

fix(vdd): share producer probe for direct capture#736
qiin2333 wants to merge 2 commits into
masterfrom
codex/vdd-producer-probe

Conversation

@qiin2333

Copy link
Copy Markdown
Collaborator

改了啥呢

  • 把 VDD shared-frame producer 的 Meta_* 探测结果抽到 vdd_utils,让 capture backend 复用同一套 exact / stale / missing / no match 判断。
  • display_vdd 继续只接受尺寸精确匹配的 producer,保留 stale producer 的拒绝保护。
  • 没有在 session 层自动 destroy/create 或二次 apply display config,避免为了一个杂鱼 stale metadata 把显示生命周期搅太大。

为啥要改

用户日志里 VDD 已经切到 2584x1828,但 producer metadata 还停在 3840x2160,于是 capture 初始化拒绝 stale producer 并结束会话。这个 PR 先把判断逻辑收口,避免后续 session/capture 各写一份探测规则,也让这个状态更容易诊断和扩展。

验证

  • git diff --check
  • src/display_device/vdd_utils.cppsrc/platform/windows/display_vdd.cpp 用 CMake/Ninja 同等宏与 flags 做 -fsyntax-only 验证
  • 用 named file mapping harness 模拟:no producer、stale sole producer、delayed producer refresh、multiple producers no match、exact match

@coderabbitai

coderabbitai Bot commented Jun 19, 2026

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: e6f2d620-91ce-4ffe-9697-6b22e041ed14

📥 Commits

Reviewing files that changed from the base of the PR and between 7a502c7 and adf9fd2.

📒 Files selected for processing (1)
  • src/display_device/vdd_utils.cpp
🚧 Files skipped from review as they are similar to previous changes (1)
  • src/display_device/vdd_utils.cpp

Summary by CodeRabbit

  • New Features
    • 增强 VDD 虚拟显示驱动的生产者检测:支持基于共享元数据的探测、状态结果返回,以及在指定时间窗口内自动重试,直至满足精确匹配条件。
  • Refactor
    • 优化监视器索引解析流程:由统一的“探测+等待”机制替代旧的直接扫描逻辑,在精确匹配成功后返回对应索引,并同步调整日志与失败路径策略。

Walkthrough

display_vdd.cpp 中内联的 Global\ZakoVDD_Meta_<i> 共享内存探测逻辑提取到 vdd_utils:在头文件中新增 vdd_producer_status_e 枚举、vdd_producer_probe_t 结构体及两个函数声明;在实现文件中定义二进制兼容的结构体与 probe/wait 函数;display_vdd.cpp 移除本地实现并改为调用新 API。

Changes

VDD 生产者探测逻辑集中化

Layer / File(s) Summary
公开类型与函数声明
src/display_device/vdd_utils.h
新增 vdd_producer_status_e 枚举、vdd_producer_probe_t 结果结构体(含 exact_match() 方法)及 probe_vdd_producer/wait_for_vdd_producer 函数声明,带默认参数。
SharedFrameMetadata 结构体与 probe/wait 实现
src/display_device/vdd_utils.cpp
定义 SharedFrameMetadata 二进制兼容结构与 VDD_META_MAGIC/VDD_META_VERSION 校验常量,配套 static_assert 布局约束;实现 calculate_exponential_backoff 指数退避、probe_vdd_producer(遍历共享内存映射、校验 Magic 并更新探测状态)及 wait_for_vdd_producer(重试窗口循环直到精确匹配或超时)。
display_vdd.cpp 调用方替换
src/platform/windows/display_vdd.cpp
新增 vdd_utils.h 引用;移除本地 vdd_probe_result_tprobe_vdd_monitor_index 实现;resolve_vdd_monitor_index 改为调用 wait_for_vdd_producer 并基于 last_result.exact_match() 返回精确索引;更新 display_vdd_vram_t::init 中的注释。

Sequence Diagram(s)

sequenceDiagram
  participant display_vdd as display_vdd.cpp<br>resolve_vdd_monitor_index
  participant wait_fn as wait_for_vdd_producer
  participant probe_fn as probe_vdd_producer
  participant shm as 共享内存<br>Global\ZakoVDD_Meta_i

  rect rgba(70, 130, 180, 0.5)
    display_vdd->>wait_fn: target_w, target_h, retry_window=2500ms, retry_delay=100ms
    loop 重试直到 exact_match() 或超时
      wait_fn->>probe_fn: target_w, target_h, max_probe=16
      loop i = 0..max_probe-1
        probe_fn->>shm: OpenFileMapping + MapViewOfFile
        shm-->>probe_fn: SharedFrameMetadata {Magic, W, H, Format, HDR}
        probe_fn->>probe_fn: 校验 VDD_META_MAGIC,更新有效计数与精确匹配索引
      end
      probe_fn-->>wait_fn: vdd_producer_probe_t (status, exact_index, valid_count)
      wait_fn->>wait_fn: 若未精确匹配则 sleep(retry_delay)
    end
    wait_fn-->>display_vdd: vdd_producer_probe_t (last_result)
  end
  display_vdd->>display_vdd: last_result.exact_match() → 返回 exact_index
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

  • AlkaidLab/foundation-sunshine#609:与本 PR 直接重叠——同样将 Global\ZakoVDD_Meta_<i> 探测/等待逻辑集中到 vdd_utils,并更新 display_vdd.cpp 以调用 wait_for_vdd_producer
  • AlkaidLab/foundation-sunshine#707:两个 PR 均修改 display_vdd.cpp 中 VDD 监视器/生产者元数据匹配路径,涉及监视器索引探测与精确匹配控制流逻辑。
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed 标题与PR主要变更一致,清晰概括了将VDD生产端探测逻辑提取到共享模块的核心改动。
Description check ✅ Passed 描述详细阐述了改动内容、改动原因及验证方法,与PR中多个文件的变更直接对应且逻辑清晰。
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/vdd-producer-probe

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@qiin2333
qiin2333 marked this pull request as ready for review June 19, 2026 08:59

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/display_device/vdd_utils.cpp`:
- Around line 116-127: The validity check for the SharedFrameMetadata currently
only verifies the Magic field against VDD_META_MAGIC, which can lead to false
positives when the producer Version is incompatible. The probe phase should also
validate that meta->Version is compatible. Update the valid boolean variable
assignment to include an additional check for meta->Version along with the
existing Magic verification, ensuring that subsequent vdd_capture_t::init calls
will not fail due to version incompatibility and preventing inconsistency
between the probe result and actual usability.
- Around line 76-89: The SharedFrameMetadata struct is used for cross-process
shared memory and currently relies only on comments for binary compatibility.
Add compile-time assertions after the struct definition to enforce hard
constraints: use static_assert with std::is_standard_layout_v to verify the
struct has standard layout, assert the sizeof(SharedFrameMetadata) matches the
expected size to catch unexpected padding or alignment issues, and add offsetof
assertions for key fields (Magic, Width, Height, DxgiFormat, FrameCounter) to
ensure their memory positions remain stable across compiler versions and
platforms.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: d989de6b-8e40-4520-9e6a-bf1c42845d9e

📥 Commits

Reviewing files that changed from the base of the PR and between 5cb8f35 and 7a502c7.

📒 Files selected for processing (3)
  • src/display_device/vdd_utils.cpp
  • src/display_device/vdd_utils.h
  • src/platform/windows/display_vdd.cpp
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Windows
🧰 Additional context used
📓 Path-based instructions (2)
src/**/*.{cpp,c,h}

⚙️ CodeRabbit configuration file

src/**/*.{cpp,c,h}: Sunshine 核心 C++ 源码,自托管游戏串流服务器。审查要点:内存安全、 线程安全、RAII 资源管理、安全漏洞。注意预处理宏控制的平台相关代码。

Files:

  • src/platform/windows/display_vdd.cpp
  • src/display_device/vdd_utils.h
  • src/display_device/vdd_utils.cpp
src/platform/**

⚙️ CodeRabbit configuration file

src/platform/**: 平台抽象层代码(Windows/Linux/macOS)。确保各平台实现一致, 注意 Windows API 调用的错误处理和资源释放。

Files:

  • src/platform/windows/display_vdd.cpp
🔇 Additional comments (2)
src/display_device/vdd_utils.h (1)

60-83: LGTM!

Also applies to: 137-150

src/platform/windows/display_vdd.cpp (1)

18-18: LGTM!

Also applies to: 279-288, 321-322

Comment thread src/display_device/vdd_utils.cpp
Comment thread src/display_device/vdd_utils.cpp

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR centralizes ZakoVDD shared-frame producer metadata probing into vdd_utils so both the display-device session layer and the VDD direct-capture backend can use the same logic to classify producers as exact / stale / missing / no-match, improving consistency and diagnosability when producer metadata lags behind the requested mode.

Changes:

  • Moved VDD Meta_* probing and retry/wait logic into display_device::vdd_utils (probe_vdd_producer / wait_for_vdd_producer).
  • Updated the Windows VDD direct-capture backend to reuse the shared probe logic while still enforcing exact size matches (and refusing stale sole producers).
  • Added ABI/layout assertions for the probed metadata struct to catch incompatible producer-side changes early.

Reviewed changes

Copilot reviewed 3 out of 3 changed files in this pull request and generated 1 comment.

File Description
src/platform/windows/display_vdd.cpp Replaces local VDD producer probing with vdd_utils::wait_for_vdd_producer while keeping exact-match enforcement.
src/display_device/vdd_utils.h Adds public probe result types and declares probe/wait helpers for ZakoVDD metadata.
src/display_device/vdd_utils.cpp Implements shared probing/waiting logic and adds struct layout checks for producer compatibility.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +78 to +95
// Must stay binary-compatible with the producer-side struct in ZakoVDD.
struct SharedFrameMetadata {
UINT32 Magic;
UINT32 Version;
UINT32 Width;
UINT32 Height;
UINT32 DxgiFormat;
UINT32 IsHdr;
float MaxNits;
float MinNits;
float MaxFALL;
UINT64 FrameCounter;
UINT64 LastPresentQpc;
};

static constexpr UINT32 VDD_META_MAGIC = 0x5A564446; // 'ZVDF'
static constexpr UINT32 VDD_META_VERSION = 1;

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants