[libcamera-devel] [PATCH v8 3/3] libcamera: pipeline: ipu3: Apply a requested test pattern mode

Hirokazu Honda hiroh at chromium.org
Fri Nov 26 06:08:10 CET 2021


This introduces a way to set controls immediately for a capture
in ipu3 pipeline handler. It enables to apply a test pattern mode
per frame.

Signed-off-by: Hirokazu Honda <hiroh at chromium.org>
Reviewed-by: Jacopo Mondi <jacopo at jmondi.org>
Reviewed-by: Jean-Michel Hautbois <jeanmichel.hautbois at ideasonboard.com>
---
 src/libcamera/pipeline/ipu3/ipu3.cpp | 55 +++++++++++++++++++++++++++-
 1 file changed, 53 insertions(+), 2 deletions(-)

diff --git a/src/libcamera/pipeline/ipu3/ipu3.cpp b/src/libcamera/pipeline/ipu3/ipu3.cpp
index 25490dcf..31f5f9dd 100644
--- a/src/libcamera/pipeline/ipu3/ipu3.cpp
+++ b/src/libcamera/pipeline/ipu3/ipu3.cpp
@@ -59,6 +59,7 @@ public:
 	void statBufferReady(FrameBuffer *buffer);
 	void queuePendingRequests();
 	void cancelPendingRequests();
+	void frameStart(uint32_t sequence);
 
 	CIO2Device cio2_;
 	ImgUDevice *imgu_;
@@ -76,7 +77,10 @@ public:
 
 	std::unique_ptr<ipa::ipu3::IPAProxyIPU3> ipa_;
 
+	/* Requests before queueing cio2 device. */
 	std::queue<Request *> pendingRequests_;
+	/* Requests queued in cio2 device and before passing imgu device. */
+	std::queue<Request *> processingRequests_;
 
 	ControlInfoMap ipaControls_;
 
@@ -823,6 +827,8 @@ void IPU3CameraData::cancelPendingRequests()
 		pipe()->completeRequest(request);
 		pendingRequests_.pop();
 	}
+
+	processingRequests_ = {};
 }
 
 void IPU3CameraData::queuePendingRequests()
@@ -853,6 +859,8 @@ void IPU3CameraData::queuePendingRequests()
 
 		info->rawBuffer = rawBuffer;
 
+		processingRequests_.push(request);
+
 		ipa::ipu3::IPU3Event ev;
 		ev.op = ipa::ipu3::EventProcessControls;
 		ev.frame = info->id;
@@ -1121,8 +1129,8 @@ int PipelineHandlerIPU3::registerCameras()
 		data->delayedCtrls_ =
 			std::make_unique<DelayedControls>(cio2->sensor()->device(),
 							  params);
-		data->cio2_.frameStart().connect(data->delayedCtrls_.get(),
-						 &DelayedControls::applyControls);
+		data->cio2_.frameStart().connect(data.get(),
+						 &IPU3CameraData::frameStart);
 
 		/* Convert the sensor rotation to a transformation */
 		int32_t rotation = 0;
@@ -1414,6 +1422,49 @@ void IPU3CameraData::statBufferReady(FrameBuffer *buffer)
 	ipa_->processEvent(ev);
 }
 
+void IPU3CameraData::frameStart(uint32_t sequence)
+{
+	/*
+	 * Handle the start of frame exposure signal.
+	 *
+	 * Inspect the list of pending requests waiting for a RAW frame to be
+	 * produced and apply controls for the 'next' one.
+	 *
+	 * Some controls need to be applied immediately, such as the
+	 * TestPatternMode one. Other controls are handled through the delayed
+	 * controls class.
+	 */
+
+	delayedCtrls_->applyControls(sequence);
+
+	if (!processingRequests_.empty()) {
+		/* Handle controls which are to be set ready for the next frame to start. */
+		Request *request = processingRequests_.front();
+		processingRequests_.pop();
+
+		/* Assumes applying the test pattern mode affects immediately. */
+		if (!request->controls().contains(controls::draft::TestPatternMode))
+			return;
+		const int32_t testPatternMode = request->controls().get(
+			controls::draft::TestPatternMode);
+
+		LOG(IPU3, Debug) << "Apply test pattern mode: "
+				 << testPatternMode;
+
+		int ret = cio2_.sensor()->setTestPatternMode(
+			static_cast<controls::draft::TestPatternModeEnum>(
+				testPatternMode));
+		if (ret) {
+			LOG(IPU3, Error) << "Failed to set test pattern mode: "
+					 << ret;
+			return;
+		}
+
+		request->metadata().set(controls::draft::TestPatternMode,
+					testPatternMode);
+	}
+}
+
 REGISTER_PIPELINE_HANDLER(PipelineHandlerIPU3)
 
 } /* namespace libcamera */
-- 
2.34.0.rc2.393.gf8c9666880-goog



More information about the libcamera-devel mailing list