qemu-usb/webcam: signal capturing off earlier

based on comment in Linux sources. Reduce fallback off-capturing detection
to 1s.

Issue #4078
This commit is contained in:
Alexander Boettcher 2021-05-21 14:41:38 +02:00 committed by Christian Helmuth
parent 7fcf9053b9
commit 98f524bb41
2 changed files with 29 additions and 8 deletions

View File

@ -48,8 +48,13 @@ will open and will use a Genode capture session to obtain the
frames in the rate as specified by the frame per secondes (fps) attribute. The
'vertical_flip' attribute specifies, whether the frames are shown flipped
for guests. For Windows guests the value has to be false, for Linux guests
true. The format supported by the model is in BGR3. If the 'screen_size' is set
true. The format supported by the model is YUV2 or BGR3. If the 'screen_size' is set
to true, the webcam model will try to use the screen size as provided by the
capture session. If the screen size is invalid (e.g. 0x0), the attribute
values of 'width' and 'height' will be used instead. If the 'report' attribute
is set, a report will be generated whenever the guests starts/ends capturing.
is set, a report will be generated whenever the guests starts/ends capturing and
if the capturing format choosen by the guest changes,
<capture enabled="..." format="BGR3"/>
or
<capture enabled="..." format="YUV2"/>

View File

@ -533,10 +533,13 @@ static void webcam_timeout(void *opague)
USBDevice *dev = (USBDevice *)opague;
USBWebcamState *state = USB_WEBCAM(opague);
if (!state->capture)
return;
if (!state->delayed_packet) {
unsigned const fps = 10000000u / formats[active_format()].interval;
/* capture off detection - after 2s or if in delay_packet state */
if (state->delay_packet || (state->watchdog && state->watchdog >= fps * 2)) {
/* capture off detection - after 1s or if in delay_packet state */
if (state->delay_packet || (state->watchdog && state->watchdog >= fps)) {
state->capture = false;
state->delay_packet = false;
usb_webcam_capture_state_changed(state->capture);
@ -601,11 +604,24 @@ static void usb_webcam_handle_control(USBDevice * const dev,
if (length || (index != (USB_DIR_IN | DEVICE_EP_ID)))
break;
/* release packets on feature == 0 endpoint clear request */
if (!value) {
/* endpoint clear request with feature == 0 */
if (value == 0) {
/*
* UVC standard does not specify how to signal stopping of capture
* on a bulk endpoint.
* According to comment in Linux, drivers/media/usb/uvc/uvc_video.c
* uvc_video_stop_streaming(), a clear request with feature == 0
* is used as stop signal as used by Windows.
*/
USBWebcamState *state = USB_WEBCAM(dev);
if (state && state->delayed_packet)
if (state) {
if (state->delayed_packet)
state->delayed_packet = 0;
if (state->capture) {
state->capture = false;
usb_webcam_capture_state_changed(state->capture);
}
}
stall = false;
}
break;