Skip to content

Latest commit

 

History

History
76 lines (61 loc) · 3.71 KB

File metadata and controls

76 lines (61 loc) · 3.71 KB

Architecture and UX contract

Scope

ZakoVirtualGamepad is deliberately a narrow DS5 backend. It does not replace ViGEm's Xbox 360 or DS4 devices and it does not accept caller-provided HID descriptors, vendor IDs, product IDs, or arbitrary feature-report handlers. That keeps the privileged attack surface small and makes compatibility behavior reviewable.

Moonlight input -> Sunshine mapping -> Zako client API -> private IOCTLs
                                                |
                                                v
                                    UMDF 2 driver + VHF
                                                |
                                                v
                               Windows HID stack / virtual DualSense

Game output (rumble/LED/triggers) -> VHF callback -> semantic output event
                                                   -> Sunshine -> Moonlight

Each open control handle owns at most one virtual controller. Closing the handle destroys the child synchronously. This ownership model makes crash recovery predictable and permits several Sunshine sessions without global device IDs.

Runtime behavior

  1. Sunshine opens \\.\ZakoVirtualGamepad with overlapped I/O.
  2. It calls GET_DRIVER_INFO and validates both protocol and capabilities.
  3. It calls CREATE_DUALSENSE with a stable locally administered MAC address.
  4. It always keeps one READ_OUTPUT request pending.
  5. Input is submitted only when changed or when Sunshine's keepalive policy requires it. The driver does not impose a polling-rate timer.
  6. On session shutdown Sunshine cancels output I/O, calls DESTROY_DEVICE, and closes the handle. Close is the authoritative cleanup path.

The output path retains the latest feedback command if no read is pending. It does not retain an unbounded history because rumble and LED commands are state, not an audit stream. A monotonically increasing sequence lets Sunshine detect coalescing.

UX requirements for Sunshine

  • Label the option DualSense (native, experimental) until the compatibility matrix and signing pipeline reach release status.
  • If unavailable, show the exact reason: not installed, access denied, protocol mismatch, or device creation failure.
  • Offer Use DualShock 4 compatibility mode as the primary recovery action.
  • Never ask a normal user to enable Windows test-signing mode.
  • Driver install/update should be a separate elevated action with progress, publisher identity, reboot state, and a rollback path.
  • Preserve the user's explicit controller choice across restarts, but do not repeatedly show modal errors when no gamepad session is active.

Concurrency and performance

There is no UMDF-specific fixed polling-rate limit. SUBMIT_INPUT directly calls VhfReadReportSubmit; practical latency depends on scheduling, HID consumers, and Sunshine's network/input loop. The initial target is 250 Hz, with 500 Hz and 1000 Hz treated as measured compatibility goals rather than promises.

The lifecycle lock serializes create, input submission, and destroy so a VHF handle cannot be deleted while a report is being submitted. A separate state lock covers the current input snapshot and one cached output state, allowing VHF callbacks to complete without waiting behind device creation or deletion. No networking, logging, allocation, or blocking user operation belongs under the state lock. VHF operations are completed immediately inside callbacks.

Security

The device ACL permits administrators, LocalSystem, and UMDF drivers. Sunshine must therefore open the driver through its privileged service boundary rather than from the web UI. IOCTLs use fixed-size structures, validate ABI headers, and expose no generic HID construction primitive.