Commit 5f2ca73d authored by Stanimir Varbanov's avatar Stanimir Varbanov Committed by Mauro Carvalho Chehab
Browse files

media: venus: venc: Init the session only once in queue_setup



Init the hfi session only once in queue_setup and also cover that
with inst->lock.

Tested-by: default avatarFritz Koenig <frkoenig@chromium.org>
Signed-off-by: default avatarStanimir Varbanov <stanimir.varbanov@linaro.org>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab+huawei@kernel.org>
parent c8e8dabc
Loading
Loading
Loading
Loading
+64 −21
Original line number Original line Diff line number Diff line
@@ -725,7 +725,9 @@ static int venc_init_session(struct venus_inst *inst)
	int ret;
	int ret;


	ret = hfi_session_init(inst, inst->fmt_cap->pixfmt);
	ret = hfi_session_init(inst, inst->fmt_cap->pixfmt);
	if (ret)
	if (ret == -EINVAL)
		return 0;
	else if (ret)
		return ret;
		return ret;


	ret = venus_helper_set_input_resolution(inst, inst->width,
	ret = venus_helper_set_input_resolution(inst, inst->width,
@@ -762,17 +764,13 @@ static int venc_out_num_buffers(struct venus_inst *inst, unsigned int *num)
	struct hfi_buffer_requirements bufreq;
	struct hfi_buffer_requirements bufreq;
	int ret;
	int ret;


	ret = venc_init_session(inst);
	ret = venus_helper_get_bufreq(inst, HFI_BUFFER_INPUT, &bufreq);
	if (ret)
	if (ret)
		return ret;
		return ret;


	ret = venus_helper_get_bufreq(inst, HFI_BUFFER_INPUT, &bufreq);

	*num = bufreq.count_actual;
	*num = bufreq.count_actual;


	hfi_session_deinit(inst);
	return 0;

	return ret;
}
}


static int venc_queue_setup(struct vb2_queue *q,
static int venc_queue_setup(struct vb2_queue *q,
@@ -781,7 +779,7 @@ static int venc_queue_setup(struct vb2_queue *q,
{
{
	struct venus_inst *inst = vb2_get_drv_priv(q);
	struct venus_inst *inst = vb2_get_drv_priv(q);
	unsigned int num, min = 4;
	unsigned int num, min = 4;
	int ret = 0;
	int ret;


	if (*num_planes) {
	if (*num_planes) {
		if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE &&
		if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE &&
@@ -803,6 +801,13 @@ static int venc_queue_setup(struct vb2_queue *q,
		return 0;
		return 0;
	}
	}


	mutex_lock(&inst->lock);
	ret = venc_init_session(inst);
	mutex_unlock(&inst->lock);

	if (ret)
		return ret;

	switch (q->type) {
	switch (q->type) {
	case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
	case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
		*num_planes = inst->fmt_out->num_planes;
		*num_planes = inst->fmt_out->num_planes;
@@ -838,6 +843,49 @@ static int venc_queue_setup(struct vb2_queue *q,
	return ret;
	return ret;
}
}


static int venc_buf_init(struct vb2_buffer *vb)
{
	struct venus_inst *inst = vb2_get_drv_priv(vb->vb2_queue);

	inst->buf_count++;

	return venus_helper_vb2_buf_init(vb);
}

static void venc_release_session(struct venus_inst *inst)
{
	int ret;

	mutex_lock(&inst->lock);

	ret = hfi_session_deinit(inst);
	if (ret || inst->session_error)
		hfi_session_abort(inst);

	mutex_unlock(&inst->lock);

	venus_pm_load_scale(inst);
	INIT_LIST_HEAD(&inst->registeredbufs);
	venus_pm_release_core(inst);
}

static void venc_buf_cleanup(struct vb2_buffer *vb)
{
	struct venus_inst *inst = vb2_get_drv_priv(vb->vb2_queue);
	struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
	struct venus_buffer *buf = to_venus_buffer(vbuf);

	mutex_lock(&inst->lock);
	if (vb->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE)
		if (!list_empty(&inst->registeredbufs))
			list_del_init(&buf->reg_list);
	mutex_unlock(&inst->lock);

	inst->buf_count--;
	if (!inst->buf_count)
		venc_release_session(inst);
}

static int venc_verify_conf(struct venus_inst *inst)
static int venc_verify_conf(struct venus_inst *inst)
{
{
	enum hfi_version ver = inst->core->res->hfi_version;
	enum hfi_version ver = inst->core->res->hfi_version;
@@ -888,38 +936,32 @@ static int venc_start_streaming(struct vb2_queue *q, unsigned int count)
	inst->sequence_cap = 0;
	inst->sequence_cap = 0;
	inst->sequence_out = 0;
	inst->sequence_out = 0;


	ret = venc_init_session(inst);
	if (ret)
		goto bufs_done;

	ret = venus_pm_acquire_core(inst);
	ret = venus_pm_acquire_core(inst);
	if (ret)
	if (ret)
		goto deinit_sess;
		goto error;


	ret = venc_set_properties(inst);
	ret = venc_set_properties(inst);
	if (ret)
	if (ret)
		goto deinit_sess;
		goto error;


	ret = venc_verify_conf(inst);
	ret = venc_verify_conf(inst);
	if (ret)
	if (ret)
		goto deinit_sess;
		goto error;


	ret = venus_helper_set_num_bufs(inst, inst->num_input_bufs,
	ret = venus_helper_set_num_bufs(inst, inst->num_input_bufs,
					inst->num_output_bufs, 0);
					inst->num_output_bufs, 0);
	if (ret)
	if (ret)
		goto deinit_sess;
		goto error;


	ret = venus_helper_vb2_start_streaming(inst);
	ret = venus_helper_vb2_start_streaming(inst);
	if (ret)
	if (ret)
		goto deinit_sess;
		goto error;


	mutex_unlock(&inst->lock);
	mutex_unlock(&inst->lock);


	return 0;
	return 0;


deinit_sess:
error:
	hfi_session_deinit(inst);
bufs_done:
	venus_helper_buffers_done(inst, q->type, VB2_BUF_STATE_QUEUED);
	venus_helper_buffers_done(inst, q->type, VB2_BUF_STATE_QUEUED);
	if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE)
	if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE)
		inst->streamon_out = 0;
		inst->streamon_out = 0;
@@ -940,7 +982,8 @@ static void venc_vb2_buf_queue(struct vb2_buffer *vb)


static const struct vb2_ops venc_vb2_ops = {
static const struct vb2_ops venc_vb2_ops = {
	.queue_setup = venc_queue_setup,
	.queue_setup = venc_queue_setup,
	.buf_init = venus_helper_vb2_buf_init,
	.buf_init = venc_buf_init,
	.buf_cleanup = venc_buf_cleanup,
	.buf_prepare = venus_helper_vb2_buf_prepare,
	.buf_prepare = venus_helper_vb2_buf_prepare,
	.start_streaming = venc_start_streaming,
	.start_streaming = venc_start_streaming,
	.stop_streaming = venus_helper_vb2_stop_streaming,
	.stop_streaming = venus_helper_vb2_stop_streaming,