- 音视频
【免费下载链接】foundation-sunshine
Sunshine fork: an enhanced sunshine, a self-hosted game streaming host for Moonlight with HDR10/HDR Vivid, virtual displays, advanced audio, optimized encoders, and a modern control panel.
本文聚焦 Foundation Sunshine(Sunshine fork)在 Windows 平台上的原生 HDR 捕获输入与 NVIDIA DLSS NR(Neural Radiance,神经渲染增强)的集成方案:核心是hdr_filter如何在不把 SDR 变 HDR、不丢失 scRGB 宽色域与高光的前提下,让一个"只认 SDR"的神经增强模型安全处理线性 FP16 的 HDR 桌面。读完本文,你将掌握该三段式 GPU 代理管线的实现原理、nr-defaults.json与运行时校验等配置细节,以及从单元测试、硬件 smoke 到生产路径首帧编码的完整验证矩阵与尚存的工程边界。
一、核心设计原则:信号保真,而非信号转换
DLSS NR 的 HDR 集成遵循一条最根本的原则:保留会话的原始信号语义。原文档(HDR.md)对此给出了明确的三点约束:
- SDR 保持 SDR:SDR 捕获继续走 SDR 路径,模型不承担任何把 SDR 升级为 HDR 的职责;
- 原生 HDR 捕获保持线性 scRGB FP16:一直保持该格式,直到进入既有的 PQ/HLG 转换和编码器阶段,中间不允许出现"先压成 SDR 再转 HDR"的信息损失;
- 单 pre-encode 槽位下 RTX HDR 优先:如果 RTX HDR 占用了唯一的 pre-encode 处理槽位,则由 RTX HDR 接管该会话,此时 NR 对该会话保持非活跃状态。
换言之,这套设计是"HDR 保真地集成一个 SDR 模型",而不是宣称模型本身理解 HDR。文档特别强调:如果模型输出与代理输入完全一致,则残差精确为零;增强则可能有意改变局部亮度、色彩与纹理——这些都属于模型行为,而非信号转换。
二、为什么不能把捕获的 scRGB 直接喂给模型
一个关键的事实边界来自实测的 NVIDIA 运行时(文档记录的 310.8.0.0 运行时,配合驱动 616.92 测试):
- 该运行时虽然接受 FP16 资源,但会把值钳制到 0..1 范围,包括强度为零的情况;
- 因此直接把捕获的 scRGB 传入模型,会丢失带符号的宽色域值与高光信息;
- 文档给出明确警告:"资源格式支持"并不能作为"原生 HDR 模型支持"的证据。
从仓库实现看,这一判断还体现在运行时的信任链上。adapter_loader.cpp 在加载foundation_dlssnr_adapter.dll与nvngx_dlssnr.dll时会计算 SHA-256 摘要:适配器摘要必须匹配编译期内置的SUNSHINE_DLSSNR_ADAPTER_SHA256,否则报adapter_untrusted;运行时摘要则在持久化配置的 pin 值存在时强制比对,不匹配即报runtime_untrusted,未 pin 时仅在加载时计算并记录日志。这解释了后面验证矩阵中大量围绕runtime_untrusted与degraded状态的测试设计。
三、hdr_filter:三段式 GPU 代理管线
hdr_filter.*是整套方案的核心实现(hdr_filter.cpp、hdr_filter.h)。它的策略是:保留原始 FP16 纹理,向模型呈现一个 SDR 代理(proxy)。管线分为三个 GPU pass,全部内嵌在同一份 HLSL 着色器中:
3.1 prepare pass:构造 BGRA8 SDR 代理
- 以203-nit 白点归一化。着色器注释给出了换算依据:scRGB 中
1.0对应 80 nits,因此203 / 80 = 2.5375成为proxy_scale的基数; proxy_scale(c) = 2.5375 + max(0, max(c.r, max(c.g, c.b))):在归一化的同时,把超出白点的高光压缩进 BGRA8 代理的动态范围;- 代理输出为
saturate(encode(max(c, 0) / proxy_scale(c)))的 BGRA8 纹理; - 当模型分辨率低于源分辨率(
scale_percent < 100)时,prepare 通过四个双线性采样点覆盖低分辨率像素足迹(适用于 50%–100% 的缩放区间); - 特殊捷径:若输入是 SDR 且
scale_percent == 100,则直接透传原始输入给模型,跳过代理开销(见process()中if (!hdr && scale_percent_ == 100) return model_->process(input);)。
3.2 模型推理:SDR 代理上的 NR(可选光流)
- 代理帧被包装为
filter_detail::make_sdr_result结果(sdr_rec709/unorm8),并把reference_white_nits置 0 后送入模型; - 模型在同一份代理上执行 DLSS NR,
nr_motion_quality > 0时还会启用光流(optical flow)路径; - 真正执行推理的是 dlssnr_filter.cpp 中的
external_neural_enhancement_filter_t,它通过dlssnr_adapter_loader_t调用适配器的create/process/destroy,并通过全局互斥量串行化适配器调用。
3.3 resolve pass:残差解码并叠加回原始 scRGB
- 同时采样精确量化后的代理(
before)与模型增强结果(after),计算delta = decode(after) - decode(before)——由于两侧采样的是同一份量化代理,模型恒等时残差精确为零; - 将残差钳制到 ±0.25,再乘上
proxy_scale(source.rgb)缩放回 scRGB 量纲,叠加到原始像素; - 结果被钳制在
-65504..65504(FP16 可表示范围),并在非有限值时回退到原始像素; - 原始 alpha 与帧元数据完整保留:
return float4(all(isfinite(result)) ? result : source.rgb, source.a);,输出纹理格式为R16G16B16A16_FLOAT; - 文档强调:不会把任何中间 SDR 帧送入 HDR 编码器;场景元数据分析(scene metadata analysis)会通过既有转换路径读取 resolve 后的帧。
该滤波器的入口是make_hdr_compatible_filter(device, context, model, scale_percent),它在设备/上下文/模型为空或缩放比例非法(valid_nr_scale要求 20–100 且为 5 的倍数)时返回空指针;dlssnr_filter.cpp的make_filter在加载并校验适配器后,把external_neural_enhancement_filter_t包进hdr_filter_t返回。
四、与既有管线契约的衔接:frame_contract 与 pre_encode_filter
hdr_filter是 vendor-neutral 的 pre-encode 滤波契约(pre_encode_filter.h)下的一个实现,上游帧语义由 frame_contract.h 描述:
frame_domain_e:unknown / sdr_rec709 / linear_scrgb / pq_bt2020 / hlg_bt2020;pixel_encoding_class_e:automatic / unorm8 / float16;- 捕获帧描述
captured_frame_desc_t记录 domain、encoding、reference_white_nits、adapter LUID、是否借用(borrowed)与源代次。
pre_encode_filter_helpers.h 中的validate_neural_input给出了原生 HDR 输入的严格契约,这是hdr_filter决定走 HDR 代理路径的判据:
- domain 必须是
linear_scrgb; - 编码必须是
float16(R16G16B16A16_FLOAT格式); reference_white_nits必须精确等于80.0f;- 不得是借用(
borrowed == false)的资源。
对应的捕获侧映射在 frame_contract.cpp:select_wgc_capture_format在契约要求float16或"automatic + linear_scrgb"时选择R16G16B16A16_FLOAT,否则回退B8G8R8A8_UNORM;describe_dxgi_captured_frame依据格式把线性 gamma 的 FP16 帧描述为linear_scrgb,把 8 位 UNORM 帧描述为sdr_rec709。
五、配置参数与 nr-defaults.json
NR 的流默认参数由 nr_defaults.cpp 管理,持久化为nr-defaults.json(位于应用数据目录),schema version 为 1:
{ "version": 1, "enabled": true, "scale_percent": 100, "intensity": 1.0, "style": 0, "skin_structure_strength": 0.0, "auto_mask": false, "ui_correction": false, "motion_quality": 0 }各参数的合法范围(valid()校验,非法则整体拒绝加载/保存):
| 参数 | 含义 | 合法范围/取值 |
|---|---|---|
scale_percent | 模型处理分辨率相对捕获分辨率的缩放 | 20–100,且必须为 5 的倍数(valid_nr_scale) |
intensity | 增强强度 | 0.0–1.0(--zero场景即设为 0) |
style | 风格档位 | 0–4 |
skin_structure_strength | 皮肤结构强度 | 0.0–1.0 |
auto_mask | 自动遮罩 | 布尔 |
ui_correction | UI 修正 | 布尔 |
motion_quality | 光流质量档 | 0 = 零运动(禁用光流),1–3 = 光流质量档 |
这些字段最终映射到 frame_contract.h 的pre_encode_filter_config_t(nr_scale_percent / nr_intensity / nr_local_tone_strength / nr_local_structure_strength / nr_skin_structure_strength / nr_style / nr_motion_quality / nr_auto_mask / nr_ui_correction),并在 dlssnr_filter.cpp 中传入foundation_dlssnr_config_t(motion_mode由nr_motion_quality > 0决定是否为FOUNDATION_DLSSNR_MOTION_OPTICAL_FLOW)。运行时状态会经 api.cpp 暴露为nr_requested_intensity / nr_intensity / nr_requested_motion_quality / nr_motion_quality / nr_scale_percent / nr_settings_failure_reason等观测字段。
后端身份与组件文件名定义在 config.h:NR 后端 id 为alkaidlab.nvidia_dlssnr,适配器为foundation_dlssnr_adapter.dll,运行时为nvngx_dlssnr.dll;runtime_pins支持按后端 pin 运行时摘要,未 pin 时接受未 pin 的运行时(加载时计算并记录日志)。
六、验证矩阵:从单元测试到硬件 smoke
原文档给出了完整的验证分层,仓库中对应的测试目标可见 tests/CMakeLists.txt。
6.1 单元测试
pre_encode_filter_unit_tests(WARP 软件光栅化):覆盖带符号值、次正规数(subnormal)、1000/4000-nit 高光、alpha、元数据、奇数尺寸、缩放(resize)、调用者设备上下文状态恢复(SwapDeviceContextState+ClearState的 state guard),以及后端不可用时的 HDR 透传;frame_contract_unit_tests:验证 NR 保留原生 PQ/HLG 输出策略、要求私有 FP16 捕获交接(private handoff),且 NR不会成为合成 HDR 源。
6.2 硬件 smoke:dlssnr_pipeline_smoke
命令行工具位于 dlssnr_pipeline_smoke.cpp,用法为:
dlssnr_pipeline_smoke <absolute adapter path> <runtime SHA-256> [--hdr] [--zero] [--flow] [--4k] [--shared]--hdr --zero:intensity置 0,走生产级已验证加载器执行真实 NR,要求 HDR 输出与输入像素级完全一致(验证恒等模型零残差性质);--hdr --flow:motion_quality置 2 启用 NR + 光流,要求输出发生变化且保留 HDR 高光,在重复的 720p/1080p 会话上验证;--4k:增加 1080p/2160p 缩放场景,实测真实运行时在 3840x2160 下重复通过原生 HDR 处理;--shared:构造生产者 D3D11 设备、在消费者设备上打开 keyed-mutex 共享纹理,并在释放捕获所有权前完成私有拷贝,测试在首帧处理后立即回读而非只检查排空批次。
这些硬件 smoke 是显式 opt-in 检查,不是常规 CI 测试,且不证明 Moonlight 串流、游戏画质或 30 分钟会话的稳定性。
6.3 聚合硬件测试(DlssNrHardware)
DlssNrHardware.NativeHdrFirstEncodedPacket覆盖 NR → 合成 P010 写入 → 真实 HEVC NVENC 提交的整条链路,要求无需显式调用者 Flush、无 CPU 回读、无第二个 NR 帧即产出首个编码包。运行方式:
SUNSHINE_TEST_DLSSNR_ADAPTER=<绝对适配器路径> SUNSHINE_TEST_DLSSNR_SHA256=<运行时小写 SHA-256>两者缺一则跳过。本地测试产出 1 个初始 IDR 加 2 个后续包(含初始化约 1.2 秒)。注意:它使用最小化诊断 P010 写入,而非生产色彩转换;桌面捕获、真实转换路径与网络投递均不在其范围内。
后续补充的生产路径测试族:
ProductionConversionFirstEncodedPacket:经生产共享纹理交接、HDR 转换/降采样与 NVENC 代码,使用合成像素验证;DesktopCaptureFirstEncodedPacket:额外要求SUNSHINE_TEST_DLSSNR_CAPTURE=1,捕获已是 HDR 的桌面、编码首帧,再要求真实帧进入 NR 活跃状态并产出另一个包;ProductionHlgConversionFirstEncodedPacket:同样的占位帧过渡与真实 NR/NVENC 检查,但输出 HLG——PQ 与 HLG 两种变体本地均通过;ProductionUnavailableNrStillEncodesHdr:拒绝运行时 pin(不改动已安装文件),验证生产编码器初始化、启动占位帧与 3 个后续 HDR 包,以及 NRdegraded状态与runtime_untrusted原因;工厂在缺失/被拒后端时已包一层 identity fallback,主处理失败时同一 failover 包装会切换到该 fallback;ProductionHdrCaptureToSdrFirstEncodedPacket与ProductionUnavailableNrStillEncodesHdrCaptureToSdr:复现"HDR 捕获 → SDR 输出"的转换失败,并在修复后验证占位帧加 3 个真实 NR/NV12/NVENC 包。
七、端到端跟进:三个 SDR-only 门槛的消除(2026-09-20)
真实原生 HDR 测试暴露了三个残留的"仅限 SDR"门槛,均已修复:
- HTTP launch attachment:启动附加流程中的信号处理;
- opened-display filter check:打开显示器时的滤波检查;
- private texture handoff:私有纹理交接。
修复后 NR 能穿越全部三处;而SDR→HDR 滤波器仍拒绝原生 HDR 源。交接逻辑使用解析后的捕获契约(resolved capture contract),仅排除了"源已分离"这一条要求。
另一个关键修复来自配对包复测:HDR 桌面以 scRGB FP16 捕获,而客户端协商的是 SDR HEVC时,原先 NR 的捕获契约从输出 transfer 推断,导致在真实帧到达后端前就被拒绝。修复后,NR 从每个已知的SDR UNORM8 或线性 scRGB FP16 帧中解析自身输入域,不改变客户端的输出 transfer,也不改变私有交接要求;未知域仍然被拒绝,SDR→HDR 滤波器保留其严格输入契约。
八、占位帧问题与桌面捕获过渡
生产路径跟进复现了一个被拒绝的首帧:Desktop Duplication 在获知捕获格式前,可能返回一个非空白的、仅含光标的占位帧(dummy),其未知语义无法满足真实 NR 契约。修复方式是:转换阶段对这类占位帧绕过增强,保留正常启动视频路径,直到出现真实捕获帧。DlssNrHardware.ProductionConversionFirstEncodedPacket与DesktopCaptureFirstEncodedPacket即针对这一过渡而设计。
九、实测数据:loopback Moonlight 与吞吐量范围
9.1 Moonlight 桌面回环复测
占位帧修复后,使用官方 Moonlight 6.1、1920x1080 捕获/输出、60 fps 请求、禁用运动估计,首次 HEVC 帧成功接收解码,主机同时报告 NR 活跃、PQ 输出与场景元数据活跃。会话在 Moonlight 进程时钟上运行29:13(首帧解码在 00:06),用户以退出快捷键主动断开:
- 接收/解码/渲染59.98 fps;
- 网络与抖动丢包0.00%;
- 主机处理延迟 6.9/920.9/7.3 ms(min/max/mean),峰值成因未隔离,属整会话主机测量而非 NR 模型增量成本;
- 56 个主机采样覆盖 27.5 分钟 NR/PQ/场景元数据活跃期,私有内存稳定在1369.20–1369.36 MiB。
文档明确:这是桌面回环测试,不是 4K 串流性能或游戏画质证据;该次是主动结束的运行,不是完整的 30 分钟测试,该门槛与真实游戏评估仍是独立验收项。
9.2 配对包与吞吐量范围
较新的 Core 91080d54 / Panel 074ce83 配对包通过溯源与文件校验。一次显式 HEVC Main10/PQ 桌面会话使用 4K scRGB 捕获 + 1080p60 输出,客户端在 10:20 主动结束,报告 60 fps、零网络/抖动丢包;20 个主机采样覆盖 570.39 秒,NR、PQ、分析与元数据全部活跃——属于短时桌面证据,30 分钟稳定性与真实游戏运动质量验收被明确取消。
在隔离的 RTX 5080 / 驱动 616.92 / 运行时 310.8.0.0 环境下,4K BGRA8 NR 在 1200 帧上测得68.78 fps(14.539 ms/帧),10 帧预热后 GPU Evaluate 均值 13.869 ms;两个与三个独立进程分别约 68.4 与 68.2 fps(聚合吞吐未提升)。该测量输入已预上传、强度为 1、光流关闭、仅回读最终输出,排除游戏渲染、HDR 代理 pass、捕获与编码;此前历史 ~44 ms 的 GPU 结果未被复现,成因仍未隔离,两者都不是固定的分辨率/FPS 门槛。
十、审查边界与降级路径
- 组件引用生命周期:启动阶段同时保留两个已启用组件的引用,直到 RTSP 解析出最终线上格式;PQ 优先选择 RTX HDR,HLG/SDR 仍可选择 NR,RTSP 随后释放未使用的引用;
- hdr_mode 上报:实际的
hdr_mode跟随编码器色彩空间,而非请求的捕获策略; - SDR 源 + HDR 请求:生产回归要求 SDR 输出状态与已投递的 NVENC 包;该回退保留10-bit + Rec.709编码——位深本身不等于 HDR;
- 未知 FP16 色彩语义仍被拒绝:仅绕过 NR 不足以建立正确的下游传递函数;
- 多实例:同进程内两个 D3D11 设备与独立 NR 实例的短时交错处理、输出回读、对等销毁与重建测试通过;调用如主机一样被串行化,这不是并发 API 调用安全或多客户端串流验收,也不据此推断单实例限制;
- Panel 配套:控制面板已检查 VC++ 运行时,缺失时提供明确的提示与下载操作。
十一、结论:实验性状态与待验收门槛
综上所述,Foundation Sunshine 通过hdr_filter实现了"信号保真的 SDR 模型 HDR 集成":原始 scRGB FP16 全程保留,模型只看到 203-nit 白点归一化、高光压缩的 BGRA8 代理,残差以 ±0.25 钳制后缩放回叠,alpha 与元数据无损,任何中间 SDR 帧都不会进入 HDR 编码器。此前的首帧超时问题已解决。
但依据原文档的明确边界,该功能仍处于实验状态:完整的 30 分钟稳定性测试与真实游戏画质/运动质量评估仍是后续独立验收门槛;单次吞吐量测量不构成分辨率/FPS 承诺。对于希望深入验证的读者,可直接阅读 HDR.md 原始文档,结合 hdr_filter.cpp 的着色器实现、dlssnr_filter.cpp 的适配器加载链路,以及 dlssnr_pipeline_smoke.cpp 的硬件测试入口进行复现。
- 音视频
【免费下载链接】foundation-sunshine
Sunshine fork: an enhanced sunshine, a self-hosted game streaming host for Moonlight with HDR10/HDR Vivid, virtual displays, advanced audio, optimized encoders, and a modern control panel.
相关推荐
Foundation Sunshine 的 NVIDIA Optical Flow(NVOF)头文件集成与 DLSS NR 运动矢量管线解析
Foundation Sunshine 的 NVIDIA Optical Flow(NVOF)头文件集成与 DLSS NR 运动矢量管线解析 本文聚焦 Foun
音视频Foundation Sunshine 硬件光流验证指南:DLSS NR 适配器的 NVOF 诊断与冒烟测试
Foundation Sunshine 硬件光流验证指南:DLSS NR 适配器的 NVOF 诊断与冒烟测试 导读 本文是 Foundation Sunshin
音视频foundation-sunshine 原生侧载组件合同:DLSS NR / RTX Video 增强组件的可信安装、版本与生命周期管理
foundation sunshine 原生侧载组件合同:DLSS NR / RTX Video 增强组件的可信安装、版本与生命周期管理 本文是 foundat
音视频
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考