Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 994d5375 authored by Laurent Pinchart's avatar Laurent Pinchart Committed by Mauro Carvalho Chehab
Browse files

[media] omap3isp: isp: Reset the ISP when the pipeline can't be stopped



When a failure to stop a module in the pipeline is detected, the only
way to recover is to reset the ISP. However, as other users can be using
a different pipeline with other modules, the ISP can't be reset
synchronously with the error detection.

Mark the ISP as needing a reset when a failure to stop a pipeline is
detected, and reset the ISP when the last user releases the last
reference to the ISP.

Modify the omap3isp_pipeline_set_stream() function to record the new ISP
pipeline state only when no error occurs, except when stopping the
pipeline in which case the pipeline is still marked as stopped.

Signed-off-by: default avatarLaurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@redhat.com>
parent b5feda91
Loading
Loading
Loading
Loading
+12 −2
Original line number Diff line number Diff line
@@ -872,6 +872,9 @@ static int isp_pipeline_disable(struct isp_pipeline *pipe)
		}
	}

	if (failure < 0)
		isp->needs_reset = true;

	return failure;
}

@@ -884,7 +887,8 @@ static int isp_pipeline_disable(struct isp_pipeline *pipe)
 * single-shot or continuous mode.
 *
 * Return 0 if successful, or the return value of the failed video::s_stream
 * operation otherwise.
 * operation otherwise. The pipeline state is not updated when the operation
 * fails, except when stopping the pipeline.
 */
int omap3isp_pipeline_set_stream(struct isp_pipeline *pipe,
				 enum isp_pipeline_stream_state state)
@@ -895,6 +899,8 @@ int omap3isp_pipeline_set_stream(struct isp_pipeline *pipe,
		ret = isp_pipeline_disable(pipe);
	else
		ret = isp_pipeline_enable(pipe, state);

	if (ret == 0 || state == ISP_PIPELINE_STREAM_STOPPED)
		pipe->stream_state = state;

	return ret;
@@ -1481,6 +1487,10 @@ void omap3isp_put(struct isp_device *isp)
	if (--isp->ref_count == 0) {
		isp_disable_interrupts(isp);
		isp_save_ctx(isp);
		if (isp->needs_reset) {
			isp_reset(isp);
			isp->needs_reset = false;
		}
		isp_disable_clocks(isp);
	}
	mutex_unlock(&isp->isp_mutex);
+1 −0
Original line number Diff line number Diff line
@@ -262,6 +262,7 @@ struct isp_device {
	/* ISP Obj */
	spinlock_t stat_lock;	/* common lock for statistic drivers */
	struct mutex isp_mutex;	/* For handling ref_count field */
	bool needs_reset;
	int has_context;
	int ref_count;
	unsigned int autoidle;