From patchwork Wed Nov 11 20:13:48 2026 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Milan Zamazal X-Patchwork-Id: 28867 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id BE808C3304 for ; Wed, 11 Nov 2026 20:14:10 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 7A10A6917C; Wed, 11 Nov 2026 21:14:10 +0100 (CET) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=redhat.com header.i=@redhat.com header.b="F/bX91nJ"; dkim-atps=neutral Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 6295368F9F for ; Wed, 11 Nov 2026 21:14:08 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1794428047; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=1n5T+TXRzWYNZC7txybOoecX5qXShCcjspxNvcFyJpk=; b=F/bX91nJe8aPDlZEWXmF1iqXC75RAcUa2x8WCfxL2cGpHkfOgnwF6S8dIKPTSAKpPYfdCQ D4VJG7gLwFAWJWkmEv6gqgLF1PpfCSsFhNN36xSf8FU3qW7QoaihKQV7jNUPyiQh8Jzr5o MfZrThNnNZo+84f86Wf7gbB+oG6tLDU= Received: from mx-prod-mc-06.mail-002.prod.us-west-2.aws.redhat.com (ec2-35-165-154-97.us-west-2.compute.amazonaws.com [35.165.154.97]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-610-htccj3GANficKLHA9FZOfg-1; Wed, 11 Nov 2026 15:14:02 -0500 X-MC-Unique: htccj3GANficKLHA9FZOfg-1 X-Mimecast-MFC-AGG-ID: htccj3GANficKLHA9FZOfg_1794428041 Received: from mx-prod-int-01.mail-002.prod.us-west-2.aws.redhat.com (mx-prod-int-01.mail-002.prod.us-west-2.aws.redhat.com [10.30.177.4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by mx-prod-mc-06.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTPS id 1A01F1800547; Wed, 11 Nov 2026 20:14:01 +0000 (UTC) Received: from mzamazal-thinkpadp1gen7.redhat.corp (headnet04.pony-001.prod.iad2.dc.redhat.com [10.2.32.116]) by mx-prod-int-01.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTP id 74C4530000E5; Wed, 11 Nov 2026 20:13:59 +0000 (UTC) From: Milan Zamazal To: libcamera-devel@lists.libcamera.org Cc: Milan Zamazal , Kieran Bingham , Jacopo Mondi Subject: [RFC PATCH v2 1/2] libcamera: software_isp: Use shared stats Date: Wed, 11 Nov 2026 21:13:48 +0100 Message-ID: <20261111201351.39373-2-mzamazal@redhat.com> In-Reply-To: <20261111201351.39373-1-mzamazal@redhat.com> References: <20261111201351.39373-1-mzamazal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.4.1 on 10.30.177.4 X-Mimecast-Spam-Score: 0 X-Mimecast-MFC-PROC-ID: 9MgXREWtRZQemGkdEbk9PP3PmH9ggsOQu_mXbcgIlFU_1794428041 X-Mimecast-Originator: redhat.com content-type: text/plain; charset="US-ASCII"; x-default=true X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" The SwStatsCpu instance created in SoftwareIsp is currently moved to the corresponding debayering object. This binds the stats to debayering, but we'd like to be able to use stats with raw output as well. Let's keep the created stats in SoftwareIsp as a shared pointer that is still passed to the debayering objects but remains accessible outside them. This also allows us to get rid of Debayer::getStatsFD method. Signed-off-by: Milan Zamazal Reviewed-by: Kieran Bingham Reviewed-by: Jacopo Mondi --- .../libcamera/internal/software_isp/software_isp.h | 2 ++ src/libcamera/software_isp/debayer.cpp | 10 ---------- src/libcamera/software_isp/debayer.h | 2 -- src/libcamera/software_isp/debayer_cpu.cpp | 2 +- src/libcamera/software_isp/debayer_cpu.h | 5 ++--- src/libcamera/software_isp/debayer_egl.cpp | 2 +- src/libcamera/software_isp/debayer_egl.h | 6 ++---- src/libcamera/software_isp/software_isp.cpp | 12 ++++++------ 8 files changed, 14 insertions(+), 27 deletions(-) diff --git a/include/libcamera/internal/software_isp/software_isp.h b/include/libcamera/internal/software_isp/software_isp.h index b64910637..2f3cc5b6b 100644 --- a/include/libcamera/internal/software_isp/software_isp.h +++ b/include/libcamera/internal/software_isp/software_isp.h @@ -33,6 +33,7 @@ #include "libcamera/internal/pipeline_handler.h" #include "libcamera/internal/shared_mem_object.h" #include "libcamera/internal/software_isp/debayer_params.h" +#include "libcamera/internal/software_isp/swstats_cpu.h" namespace libcamera { @@ -102,6 +103,7 @@ private: DmaBufAllocator dmaHeap_; bool ccmEnabled_; bool lscEnabled_; + std::shared_ptr stats_; std::unique_ptr ipa_; std::deque queuedInputBuffers_; diff --git a/src/libcamera/software_isp/debayer.cpp b/src/libcamera/software_isp/debayer.cpp index 4f6659000..547533263 100644 --- a/src/libcamera/software_isp/debayer.cpp +++ b/src/libcamera/software_isp/debayer.cpp @@ -174,16 +174,6 @@ Debayer::~Debayer() * \return The valid size ranges or an empty range if there are none */ -/** - * \fn const SharedFD &Debayer::getStatsFD() - * \brief Get the file descriptor for the statistics - * - * This file descriptor provides access to the output statistics buffer - * associated with the current debayering process. - * - * \return The file descriptor pointing to the statistics data - */ - /** * \fn unsigned int Debayer::frameSize() * \brief Get the output frame size diff --git a/src/libcamera/software_isp/debayer.h b/src/libcamera/software_isp/debayer.h index e30a05279..98d27457b 100644 --- a/src/libcamera/software_isp/debayer.h +++ b/src/libcamera/software_isp/debayer.h @@ -55,8 +55,6 @@ public: virtual SizeRange sizes(PixelFormat inputFormat, const Size &inputSize) = 0; - virtual const SharedFD &getStatsFD() = 0; - unsigned int frameSize() { return outputConfig_.frameSize; } Signal inputBufferReady; diff --git a/src/libcamera/software_isp/debayer_cpu.cpp b/src/libcamera/software_isp/debayer_cpu.cpp index 91867baa6..b69d59f70 100644 --- a/src/libcamera/software_isp/debayer_cpu.cpp +++ b/src/libcamera/software_isp/debayer_cpu.cpp @@ -93,7 +93,7 @@ DebayerCpuThread::DebayerCpuThread(DebayerCpu *debayer, unsigned int threadIndex * \param[in] stats Pointer to the stats object to use * \param[in] cm The camera manager */ -DebayerCpu::DebayerCpu(std::unique_ptr stats, const CameraManager &cm) +DebayerCpu::DebayerCpu(std::shared_ptr stats, const CameraManager &cm) : Debayer(cm), stats_(std::move(stats)) { /* diff --git a/src/libcamera/software_isp/debayer_cpu.h b/src/libcamera/software_isp/debayer_cpu.h index ae570893b..a3addac64 100644 --- a/src/libcamera/software_isp/debayer_cpu.h +++ b/src/libcamera/software_isp/debayer_cpu.h @@ -32,7 +32,7 @@ class DebayerCpuThread; class DebayerCpu : public Debayer { public: - DebayerCpu(std::unique_ptr stats, const CameraManager &cm); + DebayerCpu(std::shared_ptr stats, const CameraManager &cm); ~DebayerCpu(); int configure(const StreamConfiguration &inputCfg, @@ -47,7 +47,6 @@ public: int start() override; void stop() override; SizeRange sizes(PixelFormat inputFormat, const Size &inputSize) override; - const SharedFD &getStatsFD() override { return stats_->getStatsFD(); } private: friend class DebayerCpuThread; @@ -154,7 +153,7 @@ private: debayerFn debayer2_; debayerFn debayer3_; Rectangle window_; - std::unique_ptr stats_; + std::shared_ptr stats_; unsigned int xShift_; /* Offset of 0/1 applied to window_.x */ static constexpr unsigned int kMinThreads = 1; diff --git a/src/libcamera/software_isp/debayer_egl.cpp b/src/libcamera/software_isp/debayer_egl.cpp index 33933b11d..5f1e5ea2d 100644 --- a/src/libcamera/software_isp/debayer_egl.cpp +++ b/src/libcamera/software_isp/debayer_egl.cpp @@ -42,7 +42,7 @@ namespace libcamera { * \param[in] cm The camera manager * \param[in] display The EGL display to use */ -DebayerEGL::DebayerEGL(std::unique_ptr stats, const CameraManager &cm, EGLDisplay display) +DebayerEGL::DebayerEGL(std::shared_ptr stats, const CameraManager &cm, EGLDisplay display) : Debayer(cm), stats_(std::move(stats)), egl_(display) { } diff --git a/src/libcamera/software_isp/debayer_egl.h b/src/libcamera/software_isp/debayer_egl.h index cbbc6a450..6957452d0 100644 --- a/src/libcamera/software_isp/debayer_egl.h +++ b/src/libcamera/software_isp/debayer_egl.h @@ -40,7 +40,7 @@ class CameraManager; class DebayerEGL : public Debayer { public: - DebayerEGL(std::unique_ptr stats, const CameraManager &cm, EGLDisplay display); + DebayerEGL(std::shared_ptr stats, const CameraManager &cm, EGLDisplay display); ~DebayerEGL(); int configure(const StreamConfiguration &inputCfg, @@ -58,8 +58,6 @@ public: int start() override; void stop() override; - const SharedFD &getStatsFD() override { return stats_->getStatsFD(); } - SizeRange sizes(PixelFormat inputFormat, const Size &inputSize) override; private: @@ -121,7 +119,7 @@ private: Size nativeOutputSize_; Rectangle window_; - std::unique_ptr stats_; + std::shared_ptr stats_; eGL egl_; uint32_t width_; uint32_t height_; diff --git a/src/libcamera/software_isp/software_isp.cpp b/src/libcamera/software_isp/software_isp.cpp index 627625b4f..3b9cf3710 100644 --- a/src/libcamera/software_isp/software_isp.cpp +++ b/src/libcamera/software_isp/software_isp.cpp @@ -98,12 +98,12 @@ SoftwareIsp::SoftwareIsp(PipelineHandler *pipe, const CameraSensor *sensor, const CameraManager &cm = *pipe->cameraManager(); - auto stats = std::make_unique(cm); - if (!stats->isValid()) { + stats_ = std::make_shared(cm); + if (!stats_->isValid()) { LOG(SoftwareIsp, Error) << "Failed to create SwStatsCpu object"; return; } - stats->statsReady.connect(this, &SoftwareIsp::statsReady); + stats_->statsReady.connect(this, &SoftwareIsp::statsReady); #if HAVE_DEBAYER_EGL const GlobalConfiguration &configuration = cm._d()->configuration(); @@ -121,7 +121,7 @@ SoftwareIsp::SoftwareIsp(PipelineHandler *pipe, const CameraSensor *sensor, if (!softISPMode || softISPMode == "gpu") { auto display = eGL::probeDisplay(); if (display != EGL_NO_DISPLAY) { - debayer_ = std::make_unique(std::move(stats), cm, display); + debayer_ = std::make_unique(stats_, cm, display); } else { LOG(SoftwareIsp, Info) << "EGL not available, falling back to CPU debayer"; @@ -130,7 +130,7 @@ SoftwareIsp::SoftwareIsp(PipelineHandler *pipe, const CameraSensor *sensor, #endif if (!debayer_) - debayer_ = std::make_unique(std::move(stats), cm); + debayer_ = std::make_unique(stats_, cm); debayer_->inputBufferReady.connect(this, &SoftwareIsp::inputReady); debayer_->outputBufferReady.connect(this, &SoftwareIsp::outputReady); @@ -158,7 +158,7 @@ SoftwareIsp::SoftwareIsp(PipelineHandler *pipe, const CameraSensor *sensor, } ret = ipa_->init(IPASettings{ ipaTuningFile, sensor->model() }, - debayer_->getStatsFD(), + stats_->getStatsFD(), sharedParams_.fd(), sensorInfo, sensor->controls(),