From patchwork Mon Feb 16 20:30:26 2026 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Milan Zamazal X-Patchwork-Id: 26176 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 54EA6C0DA4 for ; Mon, 16 Feb 2026 20:30:59 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 1F3296221A; Mon, 16 Feb 2026 21:30:59 +0100 (CET) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=redhat.com header.i=@redhat.com header.b="GwGKe/mF"; 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 058656220C for ; Mon, 16 Feb 2026 21:30:56 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1771273855; 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=Ld0wUn/+nR/TQtrMxBgNUzu+VA8koimtcWOyHHwSsJU=; b=GwGKe/mFkHXryvMMQJTVFDEsOeMt5+ITEW4qqvLFgnA4JJI7svHaEC0zy9ehyDml/0dahy L7q61R58SYsanNzszriOnR1SEgtKmTBEGjp85e7x+5qa8KTX6PKox4Xz8aqMtWDB4fxvR3 6IRv6W9cqAcDVFM0x54ZcMoiirav1ow= Received: from mx-prod-mc-05.mail-002.prod.us-west-2.aws.redhat.com (ec2-54-186-198-63.us-west-2.compute.amazonaws.com [54.186.198.63]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-346--S1uuduGNz662YgwhEmjsA-1; Mon, 16 Feb 2026 15:30:54 -0500 X-MC-Unique: -S1uuduGNz662YgwhEmjsA-1 X-Mimecast-MFC-AGG-ID: -S1uuduGNz662YgwhEmjsA_1771273853 Received: from mx-prod-int-06.mail-002.prod.us-west-2.aws.redhat.com (mx-prod-int-06.mail-002.prod.us-west-2.aws.redhat.com [10.30.177.93]) (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-05.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTPS id AB80A1955D8F for ; Mon, 16 Feb 2026 20:30:53 +0000 (UTC) Received: from mzamazal-thinkpadp1gen7.tpbc.com (unknown [10.44.32.25]) by mx-prod-int-06.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTP id 6E0651800464; Mon, 16 Feb 2026 20:30:52 +0000 (UTC) From: Milan Zamazal To: libcamera-devel@lists.libcamera.org Cc: Milan Zamazal Subject: [RFC PATCH v2 07/14] libcamera: software_isp: Use multiple parameters buffers in IPA Date: Mon, 16 Feb 2026 21:30:26 +0100 Message-ID: <20260216203034.27558-8-mzamazal@redhat.com> In-Reply-To: <20260216203034.27558-1-mzamazal@redhat.com> References: <20260216203034.27558-1-mzamazal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.4.1 on 10.30.177.93 X-Mimecast-Spam-Score: 0 X-Mimecast-MFC-PROC-ID: XRy0da1NKtwDu7XMRaLctr53x5hPOBLeLKwfXv_HemA_1771273853 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" Instead of the single parameters buffer file descriptor, pass the file descriptors of all the parameters buffers to the IPA and let it use them according to the passed buffer id. This means: - The file descriptors of all the buffers must be passed to the IPA. - The IPA must store mappings of the buffer ids to the corresponding buffers. - The current buffer id is passed to/from the IPA. The parameters buffers are still copied for debayering, this will be addressed in the next patch. Signed-off-by: Milan Zamazal --- include/libcamera/ipa/soft.mojom | 2 +- src/ipa/simple/soft_simple.cpp | 41 +++++++++++---------- src/libcamera/software_isp/software_isp.cpp | 11 ++++-- 3 files changed, 30 insertions(+), 24 deletions(-) diff --git a/include/libcamera/ipa/soft.mojom b/include/libcamera/ipa/soft.mojom index f37c1e747..4738a1b46 100644 --- a/include/libcamera/ipa/soft.mojom +++ b/include/libcamera/ipa/soft.mojom @@ -15,7 +15,7 @@ struct IPAConfigInfo { interface IPASoftInterface { init(libcamera.IPASettings settings, libcamera.SharedFD fdStats, - libcamera.SharedFD fdParams, + array fdParams, libcamera.IPACameraSensorInfo sensorInfo, libcamera.ControlInfoMap sensorControls) => (int32 ret, libcamera.ControlInfoMap ipaControls, bool ccmEnabled); diff --git a/src/ipa/simple/soft_simple.cpp b/src/ipa/simple/soft_simple.cpp index 1e8b5334c..f212fabe3 100644 --- a/src/ipa/simple/soft_simple.cpp +++ b/src/ipa/simple/soft_simple.cpp @@ -53,7 +53,7 @@ public: int init(const IPASettings &settings, const SharedFD &fdStats, - const SharedFD &fdParams, + const std::vector &fdParams, const IPACameraSensorInfo &sensorInfo, const ControlInfoMap &sensorControls, ControlInfoMap *ipaControls, @@ -76,7 +76,7 @@ protected: private: void updateExposure(double exposureMSV); - DebayerParams *params_; + std::map paramsBuffers_; SwIspStats *stats_; std::unique_ptr camHelper_; ControlInfoMap sensorInfoMap_; @@ -89,13 +89,13 @@ IPASoftSimple::~IPASoftSimple() { if (stats_) munmap(stats_, sizeof(SwIspStats)); - if (params_) - munmap(params_, sizeof(DebayerParams)); + for (auto &item : paramsBuffers_) + munmap(item.second, sizeof(DebayerParams)); } int IPASoftSimple::init(const IPASettings &settings, const SharedFD &fdStats, - const SharedFD &fdParams, + const std::vector &fdParams, const IPACameraSensorInfo &sensorInfo, const ControlInfoMap &sensorControls, ControlInfoMap *ipaControls, @@ -138,8 +138,6 @@ int IPASoftSimple::init(const IPASettings &settings, return ret; *ccmEnabled = context_.ccmEnabled; - - params_ = nullptr; stats_ = nullptr; if (!fdStats.isValid()) { @@ -147,25 +145,27 @@ int IPASoftSimple::init(const IPASettings &settings, return -ENODEV; } - if (!fdParams.isValid()) { - LOG(IPASoft, Error) << "Invalid Parameters handle"; - return -ENODEV; - } + for (auto &sharedFd : fdParams) { + if (!sharedFd.isValid()) { + LOG(IPASoft, Error) << "Invalid Parameters handle"; + return -ENODEV; + } - { void *mem = mmap(nullptr, sizeof(DebayerParams), PROT_WRITE, - MAP_SHARED, fdParams.get(), 0); + MAP_SHARED, sharedFd.get(), 0); if (mem == MAP_FAILED) { LOG(IPASoft, Error) << "Unable to map Parameters"; return -errno; } - params_ = static_cast(mem); - params_->blackLevel = { { 0.0, 0.0, 0.0 } }; - params_->gamma = 1.0 / algorithms::kDefaultGamma; - params_->contrastExp = 1.0; - params_->gains = { { 1.0, 1.0, 1.0 } }; + ASSERT(sharedFd.get() >= 0); + DebayerParams *params = static_cast(mem); + params->blackLevel = { { 0.0, 0.0, 0.0 } }; + params->gamma = 1.0 / algorithms::kDefaultGamma; + params->contrastExp = 1.0; + params->gains = { { 1.0, 1.0, 1.0 } }; /* combinedMatrix is reset for each frame. */ + paramsBuffers_[sharedFd.get()] = params; } { @@ -291,9 +291,10 @@ void IPASoftSimple::computeParams(const uint32_t frame, context_.activeState.combinedMatrix = Matrix::identity(); IPAFrameContext &frameContext = context_.frameContexts.get(frame); + DebayerParams *params = paramsBuffers_.at(paramsBufferId); for (auto const &algo : algorithms()) - algo->prepare(context_, frame, frameContext, params_); - params_->combinedMatrix = context_.activeState.combinedMatrix; + algo->prepare(context_, frame, frameContext, params); + params->combinedMatrix = context_.activeState.combinedMatrix; setIspParams.emit(paramsBufferId); } diff --git a/src/libcamera/software_isp/software_isp.cpp b/src/libcamera/software_isp/software_isp.cpp index 02d1c4c12..2bc0d30b1 100644 --- a/src/libcamera/software_isp/software_isp.cpp +++ b/src/libcamera/software_isp/software_isp.cpp @@ -14,6 +14,7 @@ #include #include +#include #include #include @@ -118,6 +119,9 @@ SoftwareIsp::SoftwareIsp(PipelineHandler *pipe, const CameraSensor *sensor, if (!debayer_) debayer_ = std::make_unique(std::move(stats), configuration); + std::vector fdParams; + for (auto &item : sharedParams_) + fdParams.emplace_back(item.second.fd()); debayer_->inputBufferReady.connect(this, &SoftwareIsp::inputReady); debayer_->outputBufferReady.connect(this, &SoftwareIsp::outputReady); debayer_->releaseIspParams.connect(this, &SoftwareIsp::releaseIspParams); @@ -146,7 +150,7 @@ SoftwareIsp::SoftwareIsp(PipelineHandler *pipe, const CameraSensor *sensor, ret = ipa_->init(IPASettings{ ipaTuningFile, sensor->model() }, debayer_->getStatsFD(), - sharedParams_.begin()->second.fd(), + fdParams, sensorInfo, sensor->controls(), ipaControls, @@ -422,13 +426,14 @@ void SoftwareIsp::process(uint32_t frame, FrameBuffer *input, FrameBuffer *outpu const uint32_t paramsBufferId = availableParams_.front(); availableParams_.pop(); ipa_->computeParams(frame, paramsBufferId); + debayerParams_ = *sharedParams_.at(paramsBufferId); debayer_->invokeMethod(&Debayer::process, ConnectionTypeQueued, frame, paramsBufferId, input, output, debayerParams_); } -void SoftwareIsp::saveIspParams([[maybe_unused]] uint32_t paramsBufferId) +void SoftwareIsp::saveIspParams(uint32_t paramsBufferId) { - debayerParams_ = *sharedParams_.begin()->second; + debayerParams_ = *sharedParams_.at(paramsBufferId); } void SoftwareIsp::releaseIspParams(uint32_t paramsBufferId)