[v3,07/29] libcamera: rkisp1: Properly cancel buffers in dewarp case
diff mbox series

Message ID 20251125162851.2301793-8-stefan.klug@ideasonboard.com
State Accepted
Headers show
Series
  • Full dewarper support on imx8mp
Related show

Commit Message

Stefan Klug Nov. 25, 2025, 4:28 p.m. UTC
In case the buffer returned from the ISP was canceled, the upstream
buffer was not correctly marked as canceled. Move the cancel
functionality into an own helper function and correctly cancel the
upstream buffers. Add missing cancellation in case queuing to the
dewarper fails.

Signed-off-by: Stefan Klug <stefan.klug@ideasonboard.com>
Reviewed-by: Paul Elder <paul.elder@ideasonboard.com>
Reviewed-by: Isaac Scott <isaac.scott@ideasonboard.com>

---

Changes in v3:
- Collected tags
- Adapted code a bit as the request handling is no longer part of
  rkisp1, but was moved to the dw100 implementation
---
 src/libcamera/pipeline/rkisp1/rkisp1.cpp | 51 +++++++++++++++---------
 1 file changed, 33 insertions(+), 18 deletions(-)

Patch
diff mbox series

diff --git a/src/libcamera/pipeline/rkisp1/rkisp1.cpp b/src/libcamera/pipeline/rkisp1/rkisp1.cpp
index dbd6bf9673ff..b56b306f1ad1 100644
--- a/src/libcamera/pipeline/rkisp1/rkisp1.cpp
+++ b/src/libcamera/pipeline/rkisp1/rkisp1.cpp
@@ -207,6 +207,7 @@  private:
 	int initLinks(Camera *camera, const RkISP1CameraConfiguration &config);
 	int createCamera(MediaEntity *sensor);
 	void tryCompleteRequest(RkISP1FrameInfo *info);
+	void cancelDewarpRequest(RkISP1FrameInfo *info);
 	void imageBufferReady(FrameBuffer *buffer);
 	void paramBufferReady(FrameBuffer *buffer);
 	void statBufferReady(FrameBuffer *buffer);
@@ -1499,6 +1500,31 @@  void PipelineHandlerRkISP1::tryCompleteRequest(RkISP1FrameInfo *info)
 	completeRequest(request);
 }
 
+void PipelineHandlerRkISP1::cancelDewarpRequest(RkISP1FrameInfo *info)
+{
+	RkISP1CameraData *data = cameraData(activeCamera_);
+	Request *request = info->request;
+	/*
+	 * i.MX8MP is the only known platform with dewarper. It has
+	 * no self path. Hence, only main path buffer completion is
+	 * required.
+	 *
+	 * Also, we cannot completeBuffer(request, buffer) as buffer
+	 * here, is an internal buffer (between ISP and dewarper) and
+	 * is not associated to the any specific request. The request
+	 * buffer associated with main path stream is the one that
+	 * is required to be completed (not the internal buffer).
+	 */
+	for (auto [stream, buffer] : request->buffers()) {
+		if (stream == &data->mainPathStream_) {
+			buffer->_d()->cancel();
+			completeBuffer(request, buffer);
+		}
+	}
+
+	tryCompleteRequest(info);
+}
+
 void PipelineHandlerRkISP1::imageBufferReady(FrameBuffer *buffer)
 {
 	ASSERT(activeCamera_);
@@ -1540,23 +1566,7 @@  void PipelineHandlerRkISP1::imageBufferReady(FrameBuffer *buffer)
 
 	/* Do not queue cancelled frames to dewarper. */
 	if (metadata.status == FrameMetadata::FrameCancelled) {
-		/*
-		 * i.MX8MP is the only known platform with dewarper. It has
-		 * no self path. Hence, only main path buffer completion is
-		 * required.
-		 *
-		 * Also, we cannot completeBuffer(request, buffer) as buffer
-		 * here, is an internal buffer (between ISP and dewarper) and
-		 * is not associated to the any specific request. The request
-		 * buffer associated with main path stream is the one that
-		 * is required to be completed (not the internal buffer).
-		 */
-		for (auto it : request->buffers()) {
-			if (it.first == &data->mainPathStream_)
-				completeBuffer(request, it.second);
-		}
-
-		tryCompleteRequest(info);
+		cancelDewarpRequest(info);
 		return;
 	}
 
@@ -1598,10 +1608,15 @@  void PipelineHandlerRkISP1::imageBufferReady(FrameBuffer *buffer)
 	 * by the application.
 	 */
 	int ret = dewarper_->queueBuffers(buffer, request->buffers());
-	if (ret < 0)
+	if (ret < 0) {
 		LOG(RkISP1, Error) << "Cannot queue buffers to dewarper: "
 				   << strerror(-ret);
 
+		cancelDewarpRequest(info);
+
+		return;
+	}
+
 	request->metadata().set(controls::ScalerCrop, activeCrop_.value());
 }