diff --git a/daemon/src/chardev_client.c b/daemon/src/chardev_client.c index 10621cc..d3082d7 100644 --- a/daemon/src/chardev_client.c +++ b/daemon/src/chardev_client.c @@ -181,6 +181,29 @@ static int handle_req_decode(struct chardev_client *cli, req.capture_width, req.capture_height, req.capture_num_planes); + /* + * Degenerate-bitstream filter (issue #17): libva-v4l2-request- + * fourier flushes a stub packet into the OUTPUT_MPLANE queue at + * playback-pause boundaries. The payload is shorter than any + * parseable H.264 NAL (3-byte start code + 1-byte NAL header = + * 4 bytes minimum); avcodec_send_packet returns + * AVERROR_INVALIDDATA, which we used to propagate to the kernel + * as a decode failure. Firefox then marks H.264-via-VAAPI as + * broken for the session and routes every subsequent frame to + * libmozavcodec SW — pause never recovers to HW. + * + * Drop the request as a no-op decode and reply RESP_FRAME OK so + * libva's V4L2 state machine keeps its surface pool alive. + */ + if (req.bitstream_len < 4) { + log_info("REQ_DECODE cookie=%u: tiny bitstream %u bytes — dropping as no-op (pause-time sentinel)", + hdr->cookie, req.bitstream_len); + memset(&resp, 0, sizeof(resp)); + resp.status = DAEDALUS_DECODE_NO_FRAME; + return send_response(cli, DAEDALUS_MSG_RESP_FRAME, + hdr->cookie, &resp, sizeof(resp)); + } + /* * Open dmabuf-fds for every CAPTURE plane and mmap them. * If this fails we still attempt the decode (so the kernel