From nobody Mon Sep 29 21:09:37 2025 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id E6B54C2BB43 for ; Mon, 15 Aug 2022 23:54:53 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1355388AbiHOXwC (ORCPT ); Mon, 15 Aug 2022 19:52:02 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:40466 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1354816AbiHOXq2 (ORCPT ); Mon, 15 Aug 2022 19:46:28 -0400 Received: from ams.source.kernel.org (ams.source.kernel.org [145.40.68.75]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 062D6C0B72; Mon, 15 Aug 2022 13:14:51 -0700 (PDT) Received: from smtp.kernel.org (relay.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ams.source.kernel.org (Postfix) with ESMTPS id 98FCDB80EA9; Mon, 15 Aug 2022 20:14:49 +0000 (UTC) Received: by smtp.kernel.org (Postfix) with ESMTPSA id CC623C433C1; Mon, 15 Aug 2022 20:14:47 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=linuxfoundation.org; s=korg; t=1660594488; bh=Dor7/W3ES3QsiTFumcjQzHudAmM9Yj25fTUrxd5js+s=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=mhUg9RUObj5uLh574YPfHiuFZiMc8IbfL70m9gXJHudmrKgfhgzuaFcb3JmG+eZGq jxVYeiPIb/NedkrCcoqx5svtkjJgrTyGEmtYMi+IpzNc0eA26b1VR38VH+VCPvDGrp oCM8yO13gavHnk6Zb16pYnyKwI4jQQVXBhSR8590= From: Greg Kroah-Hartman To: linux-kernel@vger.kernel.org Cc: Greg Kroah-Hartman , stable@vger.kernel.org, Ming Qian , Hans Verkuil , Mauro Carvalho Chehab , Sasha Levin Subject: [PATCH 5.19 0463/1157] media: amphion: defer setting last_buffer_dequeued until resolution changes are processed Date: Mon, 15 Aug 2022 19:56:59 +0200 Message-Id: <20220815180458.136446630@linuxfoundation.org> X-Mailer: git-send-email 2.37.2 In-Reply-To: <20220815180439.416659447@linuxfoundation.org> References: <20220815180439.416659447@linuxfoundation.org> User-Agent: quilt/0.67 MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" From: Ming Qian [ Upstream commit afba6e20801ad9a2f863c52c21e609e021269d83 ] Don't set last_buffer_dequeued during dynamic resolution change, otherwise it may be cleared in handling resolution change, as streamoff may be called in dynamic resolution change. Normally, this does not happen. But we encounter a special testcase, User issue V4L2_DEC_CMD_STOP after enqueue one buffer that only contains codec config header, but not any frame data. So VPU report the parsed resolution, then report the eos event. So driver should notify user to handle resolution change first, after it's handled, set the last_buffer_dequeued. then the user can exit decoding normally. Otherwise the user may be stalled. Fixes: 6de8d628df6ef ("media: amphion: add v4l2 m2m vpu decoder stateful dr= iver") Signed-off-by: Ming Qian Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Sasha Levin --- drivers/media/platform/amphion/vdec.c | 36 ++++++++++++++--------- drivers/media/platform/amphion/vpu_v4l2.c | 2 +- 2 files changed, 23 insertions(+), 15 deletions(-) diff --git a/drivers/media/platform/amphion/vdec.c b/drivers/media/platform= /amphion/vdec.c index 3c02aa2a54aa..a5bb997b000b 100644 --- a/drivers/media/platform/amphion/vdec.c +++ b/drivers/media/platform/amphion/vdec.c @@ -178,16 +178,6 @@ static int vdec_ctrl_init(struct vpu_inst *inst) return 0; } =20 -static void vdec_set_last_buffer_dequeued(struct vpu_inst *inst) -{ - struct vdec_t *vdec =3D inst->priv; - - if (vdec->eos_received) { - if (!vpu_set_last_buffer_dequeued(inst)) - vdec->eos_received--; - } -} - static void vdec_handle_resolution_change(struct vpu_inst *inst) { struct vdec_t *vdec =3D inst->priv; @@ -234,6 +224,21 @@ static int vdec_update_state(struct vpu_inst *inst, en= um vpu_codec_state state, return 0; } =20 +static void vdec_set_last_buffer_dequeued(struct vpu_inst *inst) +{ + struct vdec_t *vdec =3D inst->priv; + + if (inst->state =3D=3D VPU_CODEC_STATE_DYAMIC_RESOLUTION_CHANGE) + return; + + if (vdec->eos_received) { + if (!vpu_set_last_buffer_dequeued(inst)) { + vdec->eos_received--; + vdec_update_state(inst, VPU_CODEC_STATE_DRAIN, 0); + } + } +} + static int vdec_querycap(struct file *file, void *fh, struct v4l2_capabili= ty *cap) { strscpy(cap->driver, "amphion-vpu", sizeof(cap->driver)); @@ -493,6 +498,8 @@ static int vdec_drain(struct vpu_inst *inst) =20 static int vdec_cmd_start(struct vpu_inst *inst) { + struct vdec_t *vdec =3D inst->priv; + switch (inst->state) { case VPU_CODEC_STATE_STARTED: case VPU_CODEC_STATE_DRAIN: @@ -503,6 +510,8 @@ static int vdec_cmd_start(struct vpu_inst *inst) break; } vpu_process_capture_buffer(inst); + if (vdec->eos_received) + vdec_set_last_buffer_dequeued(inst); return 0; } =20 @@ -1203,7 +1212,6 @@ static void vdec_event_eos(struct vpu_inst *inst) vdec->eos_received++; vdec->fixed_fmt =3D false; inst->min_buffer_cap =3D VDEC_MIN_BUFFER_CAP; - vdec_update_state(inst, VPU_CODEC_STATE_DRAIN, 0); vdec_set_last_buffer_dequeued(inst); vpu_inst_unlock(inst); } @@ -1480,10 +1488,10 @@ static int vdec_stop_session(struct vpu_inst *inst,= u32 type) vdec_update_state(inst, VPU_CODEC_STATE_SEEK, 0); vdec->drain =3D 0; } else { - if (inst->state !=3D VPU_CODEC_STATE_DYAMIC_RESOLUTION_CHANGE) + if (inst->state !=3D VPU_CODEC_STATE_DYAMIC_RESOLUTION_CHANGE) { vdec_abort(inst); - - vdec->eos_received =3D 0; + vdec->eos_received =3D 0; + } vdec_clear_slots(inst); } =20 diff --git a/drivers/media/platform/amphion/vpu_v4l2.c b/drivers/media/plat= form/amphion/vpu_v4l2.c index da455e5ab337..8a3eed957ae6 100644 --- a/drivers/media/platform/amphion/vpu_v4l2.c +++ b/drivers/media/platform/amphion/vpu_v4l2.c @@ -500,8 +500,8 @@ static int vpu_vb2_start_streaming(struct vb2_queue *q,= unsigned int count) fmt->sizeimage[1], fmt->bytesperline[1], fmt->sizeimage[2], fmt->bytesperline[2], q->num_buffers); - ret =3D call_vop(inst, start, q->type); vb2_clear_last_buffer_dequeued(q); + ret =3D call_vop(inst, start, q->type); if (ret) vpu_vb2_buffers_return(inst, q->type, VB2_BUF_STATE_QUEUED); =20 --=20 2.35.1