USB Remote Wakeup: Confirm Both Device Signaling and Host Permission
Compare the USB configuration descriptor, the host’s successful remote-wakeup feature request, and the device controller’s actual signaling path before blaming a host that stays asleep. These are separate pieces of evidence. A device can advertise remote wakeup and remember host permission while its selected driver still lacks the software operation needed to initiate it.
Applicability: this procedure covers ordinary USB 2.0 device remote wakeup, with Linux v6.12 host and gadget implementations as concrete examples. It excludes USB 3.x function suspend and OTG session-request exceptions. The proposed comparison matrix has not been run on hardware; no universal host sleep-state support or electrical signaling timing is asserted.

1. Record the configuration the host actually selected
Save the device identity, firmware build, negotiated speed, selected configuration, interface drivers, host controller, port topology, and intended host sleep state. Comparing two laptops without these details can inadvertently compare different configurations or a direct connection against a docking station.
In the v6.12 USB Chapter 9 definitions, configuration bmAttributes bit 5 represents remote-wakeup capability. The separate USB_DEVICE_REMOTE_WAKEUP feature selector is 1; its position in device GET_STATUS is different from the configuration capability bit. Do not test the descriptor’s bit mask against the status response.
Decode both fields by name in the evidence report. A descriptor is an advertised capability, not proof that the current host has enabled it. If firmware offers several configurations, preserve the selected configuration’s descriptor rather than a convenient descriptor dump from another operating mode.
2. Observe permission at the USB control-transfer boundary
For a USB 2.0 device, the exact v6.12 host hub implementation enables remote wakeup using a device-recipient SET_FEATURE request with USB_DEVICE_REMOTE_WAKEUP. Its disabling operation uses CLEAR_FEATURE. In usb_port_suspend(), a failed enable request aborts an autosuspend attempt, while the system-sleep path handles that failure differently and can continue. Thus successful host system suspend alone does not establish successful remote-wakeup permission.
Capture the request and its completion, not just a userspace policy write. If the request stalls or times out, retain that result beside the eventual suspend outcome. A log saying that wakeup was desired describes intent; a completed control transaction is evidence about what was communicated to the device.
The Linux USB power-management guide distinguishes runtime autosuspend from system suspend and explains that changing power/wakeup while a device is suspended affects a subsequent suspend. Set policy before the experiment and begin a fresh suspend cycle. Do not assume a late sysfs write changed permission already established for the current interval.
3. Audit the device’s signaling operation separately
The v6.12 DWC2 gadget source provides a useful implementation counterexample. Its control-request handler updates remote_wakeup_allowed for SET_FEATURE and CLEAR_FEATURE, and its device GET_STATUS handler reports that state. However, its dwc2_hsotg_gadget_ops table does not register a wakeup callback.
The gadget core’s usb_gadget_wakeup() returns -EOPNOTSUPP when that callback is absent. Consequently, host permission and a successful status read do not imply that this generic API can initiate remote wakeup through the unmodified v6.12 DWC2 driver. This is a source-level result for that driver and tag, not a claim that every DWC2 integration or vendor kernel has the same limitation.
Inspect the actual deployed operations table and record the return from the attempted wake request. Do not patch a descriptor to advertise a feature merely because a controller block appears capable in a marketing summary. A usable path also needs implemented driver support and the appropriate powered hardware resources.
4. Build a matrix with meaningful negative controls
For each host and topology, propose four cases: normal active traffic; suspended device with permission absent; suspended device with permission established; and a fresh connection or configuration cycle followed by a new permission audit. Add a deliberate unsupported-driver case when a safe development fixture makes that possible.
In the permission-absent case, verify that firmware does not initiate ordinary remote-wakeup signaling in response to the selected trigger. In the permission-present case, record the trigger, device suspend state, software request result, observed bus signaling, host resume evidence, and first successful application transaction. These checkpoints distinguish refusal, missing implementation, missing signal, and an upstream resume failure.
Do not issue diagnostic GET_STATUS transfers during the intended quiet suspended interval merely to check a cached assumption. Such traffic changes the experiment. Inspect permission before suspend or use retained device instrumentation that does not itself resume the bus. Document any instrumentation that changes clock or power state.
5. Separate device resume from whole-host wake
First qualify remote wake while the host remains running and the USB device is runtime-suspended. Then test each supported system sleep state separately. Success in the first case demonstrates a narrower path than waking an entire platform whose controller, hub, or upstream wake route may be in a different state.
Compare direct attachment and the intended hub chain while keeping firmware and trigger constant. Record hub identity and power arrangement. If signaling leaves the device but the host never resumes, preserve the bus observation and investigate the upstream path rather than repeatedly changing the device descriptor.
A hypothetical comparison might show the same permission request succeeding on both hosts, but only one topology producing a host resume. That would narrow investigation beyond the permission transaction; it would not, by itself, prove a defective hub. Conversely, an API rejection before any signaling is attempted is not evidence of a host electrical problem.
6. Release a supported configuration, not a broad promise
The qualification record should name the tested host state, driver versions, USB speed, topology, descriptor bytes, completed feature request, device request result, and post-resume transaction. Mark missing observations explicitly. Keep re-enumeration and configuration changes as new test epochs rather than carrying permission conclusions across them.
Accept the feature only when permission, implementation, signaling, and functional recovery agree for the supported combinations. Where support is absent, choose a supported controller path or document the limitation. Retrying a missing wakeup callback cannot create the feature, and repeatedly asserting a wake trigger cannot establish host permission.