ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

foundation-sunshine 的 Windows 双端目录映射:基于配对身份的 WSS 双向文件 RPC 设计解析

foundation-sunshine 的 Windows 双端目录映射:基于配对身份的 WSS 双向文件 RPC 设计解析 音视频【免费下载链接】foundation-sunshineSunshine 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.项目地址https://gitcode.com/gh_mirrors/sunshine5/foundation-sunshine点击查看免费下载本技术指南深入剖析 foundation-sunshineSunshine fork在 Windows 双端主机与 moonlight-qt 客户端之间实现会话级目录映射的完整设计方案它如何以「mapping_id 相对路径」取代绝对路径、如何复用现有配对证书与 GameStream HTTPS 端口做能力发现、如何用 Boost.Beast 承载双向文件 RPC 数据面以及第一阶段只读执行器与 smoke 验证通道的落地细节。读完本文你将掌握该特性的配置模型、路径安全边界、连接与消息协议以及源码中对应的实现模块与测试佐证可直接用于理解、部署或二次开发这套文件通道。设计定位目录映射不是 SMB而是会话级双向文件 RPC按设计文档 windows_directory_mapping_design.md 的定位本方案不把目录映射设计成 SMB 或驱动级共享而是基于现有配对身份的双向文件 RPC 通道虚拟盘WinFsp/Dokany只是 RPC 的一个前端并非第一版核心。核心设计原则可归纳为六条远端永远不能直接提交本机绝对路径文件访问统一使用mapping_id relative_path拥有本地文件系统的一端负责路径解析、权限判断和实际 I/O文件传输不进入视频、音频、输入、Limelight control stream 热路径Moonlight 作为主动连接方建立双向通道避免 NAT 与客户端防火墙问题复用现有配对证书和会话生命周期不引入额外账号体系第一版优先可靠、安全、可调试再考虑虚拟盘体验。整体架构从「Windows Explorer 右键目录」到「Rust GUI / Control Panel 快速共享入口」最终汇入 Sunshine core 与 moonlight-qt 两侧的本地目录授权、路径解析/权限检查与文件读写模块二者通过WSS/HTTPS bidirectional file RPC相连两端可选挂载 WinFsp/Dokany。分层边界上Rust GUI / Control Panel 是用户体验与配置编排层注册 Explorer 右键菜单、接收--quick-share-folder path、本机路径存在性预检、调本地管理 API、展示共享列表与审计摘要、发送系统通知Sunshine core 是安全边界和数据面持久化 mapping 配置、最终校验路径/权限/reparse point/设备授权、管理 paired client certificate 与 capability token、执行文件 I/O 与 WSS RPC、记录审计事件。文档特别强调Rust GUI 的校验只能提升体验不能替代 core 校验——来自右键菜单、Web UI、配置文件或本地 API 的任何 mapping 都必须经过 core 的同一套安全规则。双端模块划分与端口策略Sunshine 侧模块文档建议在 src/file_mapping/ 下组织新模块职责分工如下file_mapping_core配置、权限、路径解析、文件 I/Ofile_mapping_rpc请求/响应模型、handle 管理、流控、错误码file_mapping_httpHTTPS/WSS 路由注册复用 Sunshine 现有证书与客户端认证file_mapping_configmapping JSON 解析、默认值归一化、配置错误报告file_mapping::service_t内置 feature service负责 WSS 生命周期、token store、capability 状态和 mapping store 注入。路由注册方式参考clipboard_http::register_routes()避免继续膨胀confighttp.cpp。为支持右键快速共享还需新增本地管理 API仅服务本机 Control Panel / Rust GUI不走 GameStreamnvhttp只负责配置管理、不负责文件数据传输POST /api/v1/file-mapping/mappings GET /api/v1/file-mapping/mappings PATCH /api/v1/file-mapping/mappings/{id} DELETE /api/v1/file-mapping/mappings/{id}Beast WSS 数据面默认监听file_mapping_port 48020避开 GameStream/RTSP 已使用的48010。该端口允许通过配置或命令行覆盖便于多实例测试、端口冲突规避和受管环境部署capability 响应必须返回实际监听端口。在 config.cpp 中可以看到默认值file_mappings默认[]file_mapping_port默认48020并在 config.cpp 通过int_between_f限制端口范围为[1024, 65535]nvhttp.cpp 中则将这些配置注入file_mapping_configport 与 mappings_json。moonlight-qt 侧模块建议新增app/streaming/filemappinghelperclient.{h,cpp}、app/streaming/filemappingipc.{h,cpp}与file-mapping-helper/职责为Session管理 helper 生命周期FileMappingHelperClient负责启动、停止、重启 helper并通过 IPC 下发 host 地址、HTTPS 端口、证书、客户端私钥、本地目录配置file-mapping-helper负责本地文件系统访问、WSS 连接、双向 RPC 处理。该结构可直接复用现有ClipboardHelperClient、ClipboardIpc、ClipboardSync的工程模式。能力发现Sunshine 在serverinfo中暴露能力sunshineCapabilities fileMapping1/fileMapping fileMappingVersion1/fileMappingVersion /sunshineCapabilitiesmoonlight-qt 在NvHTTP::getServerInfo()后解析该能力仅当目标为 Sunshine 且能力存在时启用目录映射NVIDIA GFE 路径保持不变。映射配置模型远端永远看不到 local_root核心配置模型包含两类视图。本机完整视图拥有目录的一端保存local_root{ id: host-downloads, name: Downloads, side: host, local_root: D:\\Downloads, mode: read, allow_delete: false, allow_execute: false, follow_reparse_points: false, clients: [client_uuid], max_file_size: 10737418240 }字段约束id只能包含字母、数字、_、-mode第一阶段只允许read配置或管理 API 传入readwrite时 core 必须拒绝或降级为只读allow_delete、allow_execute、follow_reparse_points第一阶段必须保持false不开放远端删除、执行不穿透 junction/symlink/mount pointclients列出允许访问的配对客户端 UUIDmax_file_size为单文件操作上限。远端视图则只暴露{ id: host-downloads, name: Downloads, side: host, mode: read, capabilities: [list, read] }远端不应看到local_root。这一设计在 file_mapping_rpc.h 中由exposed_mapping_t结构体现——它只携带id/name/side/mode/capabilities不含任何本机路径字段。配置注入raw JSON array 与 base64 两种写法第一阶段 Sunshine 通过file_mappings配置项注入 host mappings该配置项是 JSON array[ { id: host-downloads, name: Downloads, path: C:/Users/example/Downloads, mode: read, clients: [paired-client-uuid], follow_reparse_points: false, max_file_size: 0 } ]其中clients为空表示所有已配对客户端可访问非空时只允许列出的 UUID第一阶段运行时会跳过无效 mapping并在日志中写 warning。实现字段关系值得注意配置持久化和 Web UI API 使用path表示本机真实目录运行时file_mapping::mapping_t见 file_mapping.h使用local_root保存同一值协议层和远端响应不得暴露local_root只暴露mappingid 与相对path。兼容性方面手写配置仍支持 raw JSON arrayWeb UI / control-panel 持久化时写入base64:json避免sunshine.conf行解析器把 JSON 字符串里的]、#或换行误判为配置语法。这一逻辑在 file_mapping_config.cpp 的decode_config_value中实现仅当文本以base64:前缀开头时才解码否则原样返回。配置解析的强制降级逻辑从源码看file_mapping_config.cpp 对第一版的只读约束做了强制归一化而不是简单地报错readwritemode → 写 warning「readwrite mode ignored in read-only phase」并降级为readallow_delete: true→ 写 warning 并强制falseallow_execute: true→ 写 warning 并强制falsefollow_reparse_points: true→ 写 warning 并强制falsepath不是已存在目录 → warning 并跳过该 mapping。解析结果parse_result_t同时携带mappings与warnings即「无效项跳过 有效项强制安全默认值」的双保险策略。连接流程与鉴权链条完整连接流程为Moonlight 与 Sunshine 完成配对Moonlight 获取serverinfo发现fileMappingVersion1用户启动串流Session创建FileMappingHelperClientFileMappingHelperClient启动moonlight-file-mapping-helper.exe主进程通过 IPC 将 host 地址、HTTPS 端口、服务端证书、客户端证书、客户端私钥和本地映射配置传给 helperhelper 主动连接wss://sunshine-host:https-port/api/v1/file-mapping/sessionSunshine 使用已有客户端证书识别客户端 UUID双方交换hello消息声明协议版本和各自可共享的映射文件操作均通过该双向 WSS 通道完成。鉴权链条的三个关键点源码均有对应实现授权依据是 HTTPS 客户端证书不是请求里的 UUID。Moonlight 请求 capability 时可携带IdentityManager::getUniqueId()作为诊断 hintquery 参数client_uuid或请求头X-File-Mapping-Client-UUIDSunshine 不信任其中的 UUID而是从客户端证书查 pairing store 得到内部 paired cert UUID。这一点在 file_mapping_http.cpp 中可以看到make_capability_request只是把 query 或 header 中的client_uuid读出来作为请求上下文真正的授权由register_routes传入的auth回调完成。短期一次性 session token。Sunshine 只为该 UUID 签发短期一次性 tokenWSS 建连后 Moonlight 第一条hello.client_uuid必须使用 capability 返回的client_uuid并与 token 绑定 UUID 一致。token store 实现在 file_mapping_token.h默认 TTL 60 秒、最多 128 个 token、每客户端最多 4 个、最小签发间隔 1 秒issue/consume支持一次性消费。session_url 只能来自内部可信状态。capability 响应中的session_url不能使用请求Hostheader 拼接正常情况下 capability 返回port和session_endpointMoonlight 用当前已连接的 Sunshine 主机地址自行组合 WSS 目标避免 Host header injection。这与 file_mapping_http.cpp 中make_request_session_url只采用内部session_url且剥离 query的实现一致。capability 响应结构{ ok: true, enabled: true, listening: true, version: 1, transport: wss, port: 47999, session_endpoint: /api/v1/file-mapping/session, session_url: , session_token: ..., client_uuid: sunshine-paired-cert-uuid, implementation: boost.beast }从 file_mapping_http.cpp 的make_capability_response源码看实际响应还会额外带出control: json、data: binary、featuresmappings、transfer_jobs、explicit_authorization、cancel_job与limitsbinary_header_size: 44、max_protocol_version: 1等诊断字段ok字段直接由state.error.empty()决定。RPC 消息模型与错误码控制面消息JSON text frame协议版本固定为 1file_mapping_rpc.h 中kProtocolVersion 1。消息类型枚举已覆盖hello/list/stat/open/read/close/mkdir/rename/remove/job_start/job_status/cancel/result/error。Hello声明端点角色与可共享映射{ type: hello, version: 1, endpoint: client, client_uuid: ..., mappings: [ { id: client-docs, name: Documents, side: client, mode: read } ] }List / Stat / Open / Read完整请求-响应示例{ type: list, id: 100, mapping: host-downloads, path: games/ }{ type: result, id: 100, entries: [ { name: setup.exe, kind: file, size: 123456, mtime: 1782345678 } ] }{ type: stat, id: 101, mapping: host-downloads, path: games/setup.exe }{ type: open, id: 102, mapping: host-downloads, path: games/setup.exe, mode: read }{ type: result, id: 102, handle: h-123, size: 123456 }{ type: read, id: 103, handle: h-123, offset: 0, length: 262144 }{ type: data, id: 103, eof: false, bytes_base64: ... }Write / Close / Error后续阶段语义与通用错误结构{ type: write, id: 104, handle: h-456, offset: 0, bytes_base64: ... }{ type: close, id: 105, handle: h-123 }{ type: error, id: 103, code: access_denied, message: Access denied }建议错误码全集为bad_request、unsupported_version、not_authenticated、access_denied、mapping_not_found、path_escape、not_found、already_exists、not_directory、is_directory、file_too_large、read_only、reparse_point_blocked、io_error、cancelled、rate_limited。这些错误码与 file_mapping.h 中resolve_error_e枚举invalid_mapping_id、absolute_path、invalid_relative_path、reserved_name、path_escape、reparse_point_blocked、not_found、filesystem_error等相互呼应路径解析阶段的失败会映射为对应的协议错误码。数据面JSON base64 冒烟版与 binary frame 升级路径当前 Sunshine 第一版只读执行器已实现list、stat、read/read_chunkopen在当前 read-only executor 中不提供 handle 语义必须返回unsupported_operation不能隐式路由到read。当前read响应暂时使用 JSON base64{ type: result, id: 3, ok: true, mapping: host-test, path: hello.txt, offset: 0, bytes_read: 11, total_size: 11, eof: true, encoding: base64, data: aGVsbG8gd29ybGQ }该形态用于第一阶段冒烟和 Moonlight 侧 UI/流程打通大文件传输仍应按设计升级为 WebSocket binary frame避免长期用 JSON base64 承载大块数据。实际上 file_mapping_rpc.h 已定义二进制帧魔数kBinaryMagic 0x53464d50ASCII 即 SFMP与 44 字节的binary_header_tmagic/version/flags/request_id/job_id_hash/handle_id/offset/payload_length并提供了encode_binary_header/decode_binary_header辅助函数为 binary frame 数据面预留了完整的帧头协议。moonlight-qt 侧 smoke 客户端当前 moonlight-qt 已新增app/streaming/FileMappingClient原型用于打通第一阶段capability - WSS - hello - list - readfetchCapability()请求 Sunshine GameStream HTTPS 端口上的GET /api/v1/file-mapping/capability即NvComputer::activeHttpsPort通常是 47984不是 Web UI 配置端口请求携带 MoonlightIdentityManager::getUniqueId()作为client_uuidquery 和X-File-Mapping-Client-UUIDheader主要用于诊断和兼容授权以 HTTPS 客户端证书推导出的配对 UUID 为准Sunshine capability 响应返回client_uuidpairing store 内部的配对证书 UUIDsmokeRead()使用 capability 返回的session_url和独立session_token建立 WSS实现中避免记录拼接 token 后的完整 URLhello.client_uuid使用 capability 返回的client_uuid随后发送list、read复用 Moonlight 现有客户端证书配置和 Sunshine 服务端证书 pinning当前开发环境没有 QtWebSockets 模块因此原型用QSslSocket实现最小 WebSocket handshake 与 text frame 收发只作为烟测客户端不替代后续完整产品化传输层。Session已接入隐藏烟测开关串流连接成功后会在线程池中后台执行一次smokeRead()日志输出File mapping smoke passed或失败原因该开关默认关闭不影响普通串流路径$env:MOONLIGHT_FILE_MAPPING_SMOKE1 $env:MOONLIGHT_FILE_MAPPING_SMOKE_MAPPINGhost-test $env:MOONLIGHT_FILE_MAPPING_SMOKE_PATHhello.txt可选参数MOONLIGHT_FILE_MAPPING_SMOKE_TIMEOUT_MS5000、MOONLIGHT_FILE_MAPPING_SMOKE_OFFSET0、MOONLIGHT_FILE_MAPPING_SMOKE_LENGTH4096。此外还提供不依赖完整串流 UI 的独立 smoke CLI在 moonlight-qt 仓库内构建并运行cd C:\Users\mohaha\source\repos\moonlight-qt mkdir build-filemapping-smoke cd build-filemapping-smoke cmd /c call C:\Program Files\Microsoft Visual Studio\2022\Community\Common7\Tools\VsDevCmd.bat -archx64 C:\Qt\6.8.2\msvc2022_64\bin\qmake.exe ..\filemapping-smoke\filemapping-smoke.pro -spec win32-msvc CONFIGdebug nmake$env:PATHC:\Qt\6.8.2\msvc2022_64\bin;C:\Users\mohaha\source\repos\moonlight-qt\libs\windows\lib\x64;$env:PATH .\debug\moonlight-filemapping-smoke.exe --host 127.0.0.1 --https-port 47984 --server-cert C:\path\to\sunshine-server.pem --mapping host-test --path hello.txt该工具会打印client_uuidMoonlight uniqueid并使用同一个FileMappingClient执行capability - WSS - hello - list - read。注意--https-port应使用 GameStream HTTPS 端口通常 47984NvComputer::uuid是 Sunshine 主机 UUID不能用于 WSS token/hello 绑定实际 WSShello.client_uuid使用 Sunshine capability 返回的证书配对 UUID。路径安全规则Windows 路径处理是核心安全边界文档将 Windows 路径处理定义为核心安全边界规则如下网络层路径统一使用 UTF-8 和/本地文件访问统一转换为 UTF-16 Windows API请求路径必须是相对路径禁止远端传入盘符、UNC 路径、设备路径禁止..逃逸local_root relative_path后必须 canonicalize且 canonicalize 结果必须仍位于local_root下Windows 路径比较按大小写不敏感处理默认拒绝FILE_ATTRIBUTE_REPARSE_POINT默认拒绝系统目录作为共享根如C:\Windows、C:\Program Files默认拒绝 Windows 保留设备名CON、PRN、AUX、NUL、COM1~COM9、LPT1~LPT9写入必须先进入临时文件完成后原子 rename。这些规则在 file_mapping.cpp 中有完整落地关键实现点is_valid_mapping_idL138-L147非空、长度 ≤ 64、仅允许字母/数字/_/-is_safe_relative_pathL190-L229拒绝绝对路径前导/、\、盘符前缀has_drive_prefix、UNC 前缀is_unc_like、拒绝./..段、拒绝段尾空格/点、拒绝 Windows 非法字符、、:、、\、|、?、*及控制字符、拒绝保留设备名is_reserved_windows_nameL149-L188先去除段尾空格/点再取小数点前基名做小写比较覆盖con/prn/aux/nul/com1-9/lpt1-9完整列表resolve_pathL231-L289校验 mapping id → 校验相对路径 → 校验 root 是已存在目录 → 检查 root 是否含 reparse point →weakly_canonical归一化 → 拼接root / relative→ 检查候选路径是否含 reparse point → 再次weakly_canonical→ 用path_starts_with断言结果仍在 root 下 → 按需检查存在性 → 最后再查一次 reparse pointpath_starts_withL37-L47在 Windows 下用ascii_lower做大小写不敏感比较与「Windows 路径比较按大小写不敏感」规则一致reparse point 检测L94-L130在 Windows 下用GetFileAttributesW检查FILE_ATTRIBUTE_REPARSE_POINT并沿路径逐段扫描contains_reparse_point因此 junction/symlink 无论出现在 root 还是子路径都会被拦截。性能与可靠性设计第一版建议参数分块大小默认 256 KiB 或 1 MiB单连接并发请求数限制 4~8单映射打开 handle 数限制 32支持 request id 用于响应匹配支持cancel消息取消长任务支持心跳与空闲超时大文件传输必须可恢复到明确错误状态不允许半写文件冒充完成文件。后续增强方向Range 风格断点续传、文件 hash 校验、目录 watch、传输限速、压缩策略、mmap 或零拷贝优化。WSS 传输层在 file_mapping_ws.h 中同样体现了限流思想默认最大控制帧 1 MiB、最大二进制帧 1 MiB、最大活跃会话 32、最大写队列帧 16、每会话最大 job 数 128且require_client_certificate true默认强制客户端证书。UI 方案与虚拟盘扩展双端 UI 规划Sunshine Web UI新增 Directory Mapping 配置页包含启用开关、映射列表、添加本地目录、权限选择只读/读写/允许删除、客户端授权范围、高风险操作提示moonlight-qt UI新增客户端设置——启用目录映射、选择分享给主机的本地目录、每个主机独立授权、串流中显示远端文件入口。第一版 moonlight-qt 先做文件面板不把盘符挂载作为默认入口。WinFsp/Dokany 虚拟盘可选增强推荐分层结构moonlight-qt file panel - FileMappingClient - WSS RPC可选Explorer mount - WinFsp/Dokany adapter - FileMappingClient - WSS RPC。不推荐把 WebDAV/SMB 作为默认实现——它们会引入额外认证面、缓存语义和系统服务依赖也不自然复用 Sunshine/Moonlight 已有配对身份。第三阶段可接入 WinFspWinFsp filesystem - FileMappingClient - WSS RPC - Remote FileMappingProvider挂载示例为M:\Host\Downloads、N:\Client\Documents。关键注意事项WinFsp 层只负责把 Windows 文件系统回调转成 RPC权限和路径安全仍在 provider 端执行虚拟盘失败不应影响串流未安装 WinFsp 时仍保留文件面板能力第一阶段只允许只读挂载上传、删除、rename、replace 需等写入语义和冲突处理单独设计挂载生命周期绑定 Moonlight 与对应 Sunshine 主机连接断线、退出或主机撤销共享时必须自动卸载挂载后本机任意程序都可能读取该盘符UI 必须明确提示不承诺固定盘符默认使用可读挂载名高级设置再允许指定盘符或挂载目录。HTTP 与 WSS 实现分工Sunshine 现有Simple-Web-Server适合继续承担 Web UI、REST API、GameStreamnvhttp能力发现和轻量管理接口但不应作为完整文件映射 WSS 数据通道的主要实现原因在于文件映射需要长期双向连接、WebSocket binary frame、ping/pong/close handshake/fragment/mask/backpressure以及大文件分块、取消、限速和弱网恢复——Simple-Web-Server只提供较底层的on_upgrade接管点完整 WebSocket 协议仍需自行实现。因此推荐分工Simple-Web-Server - nvhttp HTTPS /api/v1/file-mapping/capability - Web UI /api/v1/file-mapping/config - Web UI 管理接口 Boost.Beast / Boost.Asio - file mapping WebSocket session - JSON control frame - binary data frame - ping/pong, close, backpressure - transfer job lifecycle从源码结构看这一分工已落地HTTP 路由注册由 file_mapping_http.cpp 的register_routes完成^/api/v1/file-mapping/capability$与^/api/v1/file-mapping/session$两条 GET 路由WSS 监听由 file_mapping_ws_server.h 的server_t承担Boost.Asio SSL含start/stop/bound_port/state与active_sessions统计会话状态机由 file_mapping_ws.h 的session_core_t实现awaiting_hello - ready - closedhandle_text/handle_binary分发handle_hello/handle_job_status/handle_cancel/handle_operation处理器job 表由jobs_map 管理。file_mapping_http.cpp 中make_session_placeholder_response明确返回session_not_implemented并提示「file mapping websocket sessions are served by the advertised Beast endpoint」印证了 session 端点在 Simple-Web-Server 侧只做占位、真实数据面由 Beast 提供。端口策略有两种独立文件映射端口实现简单、边界清楚Moonlight 主动连出适合第一版与复用现有 HTTPS 端口体验更统一但需统一 acceptor 或从on_upgrade安全交接 socket适合后续阶段。推荐落地顺序file_mapping_http保留 capability response/model 和后续管理接口 → 新增file_mapping_ws基于 Boost.Beast 实现 session 核心 → 第一版 capability 挂到nvhttpHTTPS 端口、WSS 使用独立动态端口 → 后续再评估统一到现有 HTTPS 端口。分阶段实施路线与测试清单三个阶段的目标与交付Phase 1Sunshine → Moonlight 文件访问Sunshine 配置共享目录、moonlight-qt 文件面板浏览主机目录、支持下载固定 read-only不开放上传、删除、执行、reparse point 穿透。交付file_mapping_core、Sunshine WSS session endpoint、moonlight-qtfile-mapping-helper、moonlight-qt 文件面板。Phase 2双向目录映射moonlight-qt 配置客户端共享目录Sunshine 通过同一条 WSS 访问客户端目录双端统一使用相同 RPC 和权限模型。交付 client-side provider、Sunshine 侧 remote client mapping registry、双向权限 UI。Phase 3Windows 虚拟盘可选安装 WinFsp将远端目录只读挂载为盘符或目录断线/退出/撤销共享时自动卸载。交付 Moonlight WinFsp adapter、Sunshine WinFsp adapter可选、挂载状态 UI、可读错误提示。测试清单核心项相对路径正常解析..逃逸被拒绝盘符路径被拒绝UNC 路径被拒绝junction/symlink 默认被拒绝只读映射拒绝写入/删除/rename大文件分块读写正确中断传输不留下伪完成文件helper 崩溃后不影响串流并按限制重启reconnect 后文件通道可重新建立未启用能力的服务器不显示目录映射入口。Windows 特定测试中文路径、超长路径、大小写差异路径、保留设备名、文件被占用、权限不足、FAT/NTFS 不同行为。这些安全断言在仓库测试 test_file_mapping.cpp 中有对应覆盖针对路径解析与逃逸防护的断言在多个用例中出现。推荐结论优雅落地方式是把目录映射抽象为会话级双向文件 RPCMoonlight 主动连接 Sunshine 并复用配对证书双端各自只暴露受控 mapping不暴露真实绝对路径第一版做文件面板和稳定传输第二版完成客户端反向共享第三版用 WinFsp 提供盘符体验。这样可以在不污染串流热路径、不引入 SMB 复杂度、不要求客户端开放端口的前提下逐步获得接近本地盘的使用体验——这也正是本文所解析的 foundation-sunshine Windows 双端目录映射方案的核心价值所在。赞分享音视频【免费下载链接】foundation-sunshineSunshine 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.项目地址https://gitcode.com/gh_mirrors/sunshine5/foundation-sunshine点击查看免费下载相关推荐Genkit Reflection 协议 V2 深度解析基于 WebSocket 与 JSON-RPC 2.0 的双向反射架构Genkit Reflection 协议 V2 深度解析基于 WebSocket 与 JSON RPC 2.0 的双向反射架构 本文以 Genkit 仓库中的人工智能大模型后端AI AgentRAG工具调用告别分屏烦恼Chrome画中画扩展让你边看视频边高效工作告别分屏烦恼Chrome画中画扩展让你边看视频边高效工作 你是否经常遇到这样的困扰正在观看重要的在线课程却需要同时查阅资料或回复邮件参加视频会议时又不前端Apache Pulsar TLS 双向认证配置指南基于客户端证书的角色身份认证Apache Pulsar TLS 双向认证配置指南基于客户端证书的角色身份认证 导读 本文是 Apache Pulsar 安全体系中 TLS 认证TLS消息队列后端流处理上一篇BilibiliDown终极指南三步轻松获取B站高清视频的完整方案下一篇WzComparerR2冒险岛WZ文件解析与资源提取的终极指南创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表