From patchwork Sun Aug 24 00:48:16 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bryan O'Donoghue X-Patchwork-Id: 24187 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 0BECCBEFBE for ; Sun, 24 Aug 2025 00:48:51 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id AECE5692FB; Sun, 24 Aug 2025 02:48:46 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (2048-bit key; unprotected) header.d=linaro.org header.i=@linaro.org header.b="EKjrcheU"; dkim-atps=neutral Received: from mail-wr1-x42e.google.com (mail-wr1-x42e.google.com [IPv6:2a00:1450:4864:20::42e]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 49E74692E2 for ; Sun, 24 Aug 2025 02:48:40 +0200 (CEST) Received: by mail-wr1-x42e.google.com with SMTP id ffacd0b85a97d-3c68ac7e238so724682f8f.1 for ; Sat, 23 Aug 2025 17:48:40 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1755996520; x=1756601320; darn=lists.libcamera.org; h=cc:to:in-reply-to:references:message-id:content-transfer-encoding :mime-version:subject:date:from:from:to:cc:subject:date:message-id :reply-to; bh=64YAzBv08eBeUOixco+cD2i/qSqZ5vgWsysXTG4pROE=; b=EKjrcheUbihDK7Iw65qZfuG3M9BsgV6S6dFvMfMy5/ZVwEr+TiCUecHMgdK65C4+Xl 7vPrPCdPAagbSRMTQ1oPbIkykw0FJcf723oiq0us19IDGoDDmc7sBU21SL4MiGhhbyiR m4OalZl5/XdrbiDrXQWjv2+EKO0HKwu/dH1u0MNh+MgfnAPxKXzF0xqpv7hi7mcXWbK/ 6rRj8UASeqe9y0erS4A7RCAuIuWj5EVjH7mRCRq545dFAEZlqRnGrMQXQ1EhmzPrmsI1 3RzOGbtx7PUQknEcJduP1hQtyoTjQNhcGuvMsFQ2ZIkaGJf3BSdCOr4EYybwsVV/Ymzz 71Tw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1755996520; x=1756601320; h=cc:to:in-reply-to:references:message-id:content-transfer-encoding :mime-version:subject:date:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=64YAzBv08eBeUOixco+cD2i/qSqZ5vgWsysXTG4pROE=; b=XNPctcnAxVnkGhGf03BwP23XC4heTaHYENk6FCx9DIEDyCzIE/UwX2xUdSMxxAiixV 34RMQkLK4buhgCVq8+nFQfcJNYCpBsQoMrSxzdSmX2/TFJ+RvEFlXSwEPbeWJkxCViA9 a3Bxfbx4aLIWU4REU2TOP5ECV3c/sY329BLfab8tqSLIcjvKO/xNxkORkDhhyKW6ahyO 6BOs9pgsqJ1d4asewdjrWvYHRCEP8yspk3bHErHJVSpuQTOl2Htl3xkjImFqh3rX9gi8 yGTMEcIdi1b2U8qNbhzIoCmplBghmghQn/kJNlsitXRxTV4uvxd2NyHDZlw9JqkVsICb kG/w== X-Gm-Message-State: AOJu0Yw7aWufK1BEm1+qiizTaLzMkXbZ1ZYeqtw7Kx0+d/iNDQiDwcVh mPw/xvhiuMtR1dd+l5+vCTJn9VnCmC+zL1WL8gn8kSreycsk2gFUcWuWKL2EveN/Soc= X-Gm-Gg: ASbGncuAQ6R4hUP93Pmm775B2fSkFb1ParQQz/Wpd6Q67eBJB3/5smj1ZUaJb27fKsU bqWRPiEZyDfGCvq9LTfO+iBacbJy8BkgFJBqGG3B4W1zRMHjOf9o3VzK0ku9jQxnWa3EZ1m6hVk LKW5RU16H/Yw1rIv5qaPyJbaUWGbVsT+h1R/BeRp6A6oHbpH2ZmXnCkDA/x9HjmBA3xljl402se IlgUVqyVYWehxJrcVTdWsHgEyXvbdcsPqO7O/LzFl0hahMgC4jSP+v/1OldkYoLAWsWiRIH2OvP 9ZkP3FMptc1mCHJCKc4KYENWWPKRR7+hbQszJJzquOpmYeCCtLuxEWKixCQj6agtBf/V2QzMPxH 95XPZsA5E80YlPvsDUgFSPJxIC+rKMNw2yPe4vadLCzOU4TVKKNcH2g3j1EKsMwTIBS2uk00HS7 5Pv0saAXVtMZBhyRc0rYXe X-Google-Smtp-Source: AGHT+IFJNIUqhlrANMlkLrEGqlViKR2DG9eRyz7KNLreD23B70r06CWz1YfBxtmn3iz4BXNA0kQEtQ== X-Received: by 2002:a05:600c:45d0:b0:459:e025:8c5a with SMTP id 5b1f17b1804b1-45b517d4b94mr71756715e9.33.1755996519743; Sat, 23 Aug 2025 17:48:39 -0700 (PDT) Received: from [192.168.0.13] (188-141-3-146.dynamic.upc.ie. [188.141.3.146]) by smtp.gmail.com with ESMTPSA id 5b1f17b1804b1-45b4e1d530esm69347225e9.0.2025.08.23.17.48.39 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Sat, 23 Aug 2025 17:48:39 -0700 (PDT) From: Bryan O'Donoghue Date: Sun, 24 Aug 2025 01:48:16 +0100 Subject: [PATCH v2 04/37] libcamera: software_isp: Move benchmark code to its own class MIME-Version: 1.0 Message-Id: <20250824-b4-v0-5-2-gpuisp-v2-a-v2-4-96f4576c814e@linaro.org> References: <20250824-b4-v0-5-2-gpuisp-v2-a-v2-0-96f4576c814e@linaro.org> In-Reply-To: <20250824-b4-v0-5-2-gpuisp-v2-a-v2-0-96f4576c814e@linaro.org> To: libcamera-devel@lists.libcamera.org Cc: Bryan O'Donoghue , Hans de Goede , Kieran Bingham , Milan Zamazal X-Mailer: b4 0.14.2 X-Developer-Signature: v=1; a=openpgp-sha256; l=8718; i=bryan.odonoghue@linaro.org; h=from:subject:message-id; bh=DQzuBIbeoz7dvkzWgdJFlHALQxDxAg4mmCseoMwhdBA=; b=owEBbQKS/ZANAwAKASJxO7Ohjcg6AcsmYgBoqmFdA4vLSqqaY/cxt5GM1N5E8a7ni9aglLSfF p5o/p8j+V2JAjMEAAEKAB0WIQTmk/sqq6Nt4Rerb7QicTuzoY3IOgUCaKphXQAKCRAicTuzoY3I OjNRD/4seRhRzNzaH7P8IOOtfOwEuI3CMbhdhJ1YRt1lcKpat9hgl+z1ZaaSS6Qn36x5K7dHEFj 77OZHsr+pVuyXv0KoY9IK2NDloPZP36kSE05Aoei/zP4+TpIyzB1H6Ks4FRheLjo7GGMOtnbRP8 kKwbKCPp9vPArX1vc4oZJu+Qug4fCl6oNfXKM7e9qYxROb5xBJVGUz4YlRsENQ9JYEfvTZNXu4d Js0vKTP0/Q17JcE4xFH6cN6BWryNkvP6OXL0kcn+nvGVGYVFwjGN6P2FWsq3DjYTkjZuomGAxJ0 w3MinEuOSaWcEp4UjirMuOMBgJcUJb0Q61B7VTHllgTS+uUoXKhB2E3I1A86Bzy1+HlXB0ko9i1 aXENzgBfDsct0lSALXQbu8LDTMXq5P3QWUeqjjPuGiEOXy2LvC2wjtO/WtNsRYNRFriO5hE+qkl LB6PGVYJgLbK/UJMKq7h40X7D0KNQVJdNUrByHWGU2dVnnp+ilWZq5j1m3/As0nKSQoY9mnUUkL LJS/LP6khpv5TGfRtlNSRwRZHpXmjNeyPiDoNO1VJUpXWzNI5X6dPuLAr+cl2EO9WBs4guSwCWJ d0xjUQkcnaVLAPPemCR6P0V0WvoLPyhIYF2WA3Xhf16BKPOw0CoGlbkGgL4DWOjsPcRECsUPpVs AuSAT59vOWC61aA== X-Developer-Key: i=bryan.odonoghue@linaro.org; a=openpgp; fpr=E693FB2AABA36DE117AB6FB422713BB3A18DC83A 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" From: Hans de Goede Move the code for the builtin benchmark to its own small Benchmark class. Reviewed-by: Kieran Bingham Reviewed-by: Milan Zamazal Signed-off-by: Hans de Goede Signed-off-by: Bryan O'Donoghue --- .../libcamera/internal/software_isp/benchmark.h | 36 +++++++++ .../libcamera/internal/software_isp/meson.build | 1 + src/libcamera/software_isp/benchmark.cpp | 93 ++++++++++++++++++++++ src/libcamera/software_isp/debayer_cpu.cpp | 36 +-------- src/libcamera/software_isp/debayer_cpu.h | 7 +- src/libcamera/software_isp/meson.build | 1 + 6 files changed, 135 insertions(+), 39 deletions(-) diff --git a/include/libcamera/internal/software_isp/benchmark.h b/include/libcamera/internal/software_isp/benchmark.h new file mode 100644 index 0000000000000000000000000000000000000000..8af2501548d75e1d0bd2043c0a83e96b3af9bd52 --- /dev/null +++ b/include/libcamera/internal/software_isp/benchmark.h @@ -0,0 +1,36 @@ +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright (C) 2024, Red Hat Inc. + * + * Authors: + * Hans de Goede + * + * Simple builtin benchmark to measure software ISP processing times + */ + +#pragma once + +#include +#include + +namespace libcamera { + +class Benchmark +{ +public: + Benchmark(); + ~Benchmark(); + + void startFrame(void); + void finishFrame(void); + +private: + unsigned int measuredFrames_; + int64_t frameProcessTime_; + timespec frameStartTime_; + /* Skip 30 frames for things to stabilize then measure 30 frames */ + static constexpr unsigned int kFramesToSkip = 30; + static constexpr unsigned int kLastFrameToMeasure = 60; +}; + +} /* namespace libcamera */ diff --git a/include/libcamera/internal/software_isp/meson.build b/include/libcamera/internal/software_isp/meson.build index ea3f3f1c1dfb3a9e87921416d471b96dc2fcf992..df7c3b97dbca7f0b645a985c857ea138a10ab402 100644 --- a/include/libcamera/internal/software_isp/meson.build +++ b/include/libcamera/internal/software_isp/meson.build @@ -1,6 +1,7 @@ # SPDX-License-Identifier: CC0-1.0 libcamera_internal_headers += files([ + 'benchmark.h', 'debayer_params.h', 'software_isp.h', 'swisp_stats.h', diff --git a/src/libcamera/software_isp/benchmark.cpp b/src/libcamera/software_isp/benchmark.cpp new file mode 100644 index 0000000000000000000000000000000000000000..b3da3c4169f907bfe9cae93fe4cafac6428f54c2 --- /dev/null +++ b/src/libcamera/software_isp/benchmark.cpp @@ -0,0 +1,93 @@ +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright (C) 2024, Red Hat Inc. + * + * Authors: + * Hans de Goede + * + * Simple builtin benchmark to measure software ISP processing times + */ + +#include "libcamera/internal/software_isp/benchmark.h" + +#include + +namespace libcamera { + +LOG_DEFINE_CATEGORY(Benchmark) + +/** + * \class Benchmark + * \brief Simple builtin benchmark + * + * Simple builtin benchmark to measure software ISP processing times. + */ + +/** + * \brief Constructs a Benchmark object + */ +Benchmark::Benchmark() + : measuredFrames_(0), frameProcessTime_(0) +{ +} + +Benchmark::~Benchmark() +{ +} + +static inline int64_t timeDiff(timespec &after, timespec &before) +{ + return (after.tv_sec - before.tv_sec) * 1000000000LL + + (int64_t)after.tv_nsec - (int64_t)before.tv_nsec; +} + +/** + * \brief Start measuring process time for a single frame + * + * Call this function before processing frame data to start measuring + * the process time for a frame. + */ +void Benchmark::startFrame(void) +{ + if (measuredFrames_ >= Benchmark::kLastFrameToMeasure) + return; + + frameStartTime_ = {}; + clock_gettime(CLOCK_MONOTONIC_RAW, &frameStartTime_); +} + +/** + * \brief Finish measuring process time for a single frame + * + * Call this function after processing frame data to finish measuring + * the process time for a frame. + * + * This function will log frame processing time information after + * Benchmark::kLastFrameToMeasure frames have been processed. + */ +void Benchmark::finishFrame(void) +{ + if (measuredFrames_ >= Benchmark::kLastFrameToMeasure) + return; + + measuredFrames_++; + + if (measuredFrames_ <= Benchmark::kFramesToSkip) + return; + + timespec frameEndTime = {}; + clock_gettime(CLOCK_MONOTONIC_RAW, &frameEndTime); + frameProcessTime_ += timeDiff(frameEndTime, frameStartTime_); + + if (measuredFrames_ == Benchmark::kLastFrameToMeasure) { + const unsigned int measuredFrames = Benchmark::kLastFrameToMeasure - + Benchmark::kFramesToSkip; + LOG(Benchmark, Info) + << "Processed " << measuredFrames + << " frames in " << frameProcessTime_ / 1000 << "us, " + << frameProcessTime_ / (1000 * measuredFrames) + << " us/frame"; + } +} + +} /* namespace libcamera */ diff --git a/src/libcamera/software_isp/debayer_cpu.cpp b/src/libcamera/software_isp/debayer_cpu.cpp index 66f6038c1e765b351871b69e915fbeea23324329..8d30bf4a2115137939f01378e8af594170d4d459 100644 --- a/src/libcamera/software_isp/debayer_cpu.cpp +++ b/src/libcamera/software_isp/debayer_cpu.cpp @@ -554,9 +554,6 @@ int DebayerCpu::configure(const StreamConfiguration &inputCfg, lineBuffers_[i].resize(lineBufferLength_); } - measuredFrames_ = 0; - frameProcessTime_ = 0; - return 0; } @@ -746,24 +743,9 @@ void DebayerCpu::process4(const uint8_t *src, uint8_t *dst) } } -namespace { - -inline int64_t timeDiff(timespec &after, timespec &before) -{ - return (after.tv_sec - before.tv_sec) * 1000000000LL + - (int64_t)after.tv_nsec - (int64_t)before.tv_nsec; -} - -} /* namespace */ - void DebayerCpu::process(uint32_t frame, FrameBuffer *input, FrameBuffer *output, DebayerParams params) { - timespec frameStartTime; - - if (measuredFrames_ < DebayerCpu::kLastFrameToMeasure) { - frameStartTime = {}; - clock_gettime(CLOCK_MONOTONIC_RAW, &frameStartTime); - } + bench_.startFrame(); std::vector dmaSyncers; for (const FrameBuffer::Plane &plane : input->planes()) @@ -817,21 +799,7 @@ void DebayerCpu::process(uint32_t frame, FrameBuffer *input, FrameBuffer *output dmaSyncers.clear(); /* Measure before emitting signals */ - if (measuredFrames_ < DebayerCpu::kLastFrameToMeasure && - ++measuredFrames_ > DebayerCpu::kFramesToSkip) { - timespec frameEndTime = {}; - clock_gettime(CLOCK_MONOTONIC_RAW, &frameEndTime); - frameProcessTime_ += timeDiff(frameEndTime, frameStartTime); - if (measuredFrames_ == DebayerCpu::kLastFrameToMeasure) { - const unsigned int measuredFrames = DebayerCpu::kLastFrameToMeasure - - DebayerCpu::kFramesToSkip; - LOG(Debayer, Info) - << "Processed " << measuredFrames - << " frames in " << frameProcessTime_ / 1000 << "us, " - << frameProcessTime_ / (1000 * measuredFrames) - << " us/frame"; - } - } + bench_.finishFrame(); /* * Buffer ids are currently not used, so pass zeros as its parameter. diff --git a/src/libcamera/software_isp/debayer_cpu.h b/src/libcamera/software_isp/debayer_cpu.h index 89a89893d6c039a8d8df4ba87519becfd8fccfa3..182607cda870be6f650368479b30865c7457880e 100644 --- a/src/libcamera/software_isp/debayer_cpu.h +++ b/src/libcamera/software_isp/debayer_cpu.h @@ -17,6 +17,7 @@ #include +#include "libcamera/internal/software_isp/benchmark.h" #include "libcamera/internal/bayer_format.h" #include "libcamera/internal/software_isp/swstats_cpu.h" @@ -160,11 +161,7 @@ private: unsigned int xShift_; /* Offset of 0/1 applied to window_.x */ bool enableInputMemcpy_; bool swapRedBlueGains_; - unsigned int measuredFrames_; - int64_t frameProcessTime_; - /* Skip 30 frames for things to stabilize then measure 30 frames */ - static constexpr unsigned int kFramesToSkip = 30; - static constexpr unsigned int kLastFrameToMeasure = 60; + Benchmark bench_; }; } /* namespace libcamera */ diff --git a/src/libcamera/software_isp/meson.build b/src/libcamera/software_isp/meson.build index aac7eda7b5b3636e1a580ddb095a0ffd512e86ea..59fa5f02a0a5620fa524d8a171332f04e0f769b2 100644 --- a/src/libcamera/software_isp/meson.build +++ b/src/libcamera/software_isp/meson.build @@ -8,6 +8,7 @@ if not softisp_enabled endif libcamera_internal_sources += files([ + 'benchmark.cpp', 'debayer.cpp', 'debayer_cpu.cpp', 'software_isp.cpp',