From patchwork Mon Feb 16 19:02:01 2026 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Hans de Goede X-Patchwork-Id: 26168 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 6932BC3240 for ; Mon, 16 Feb 2026 19:02:19 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 1BB9F6220D; Mon, 16 Feb 2026 20:02:19 +0100 (CET) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (2048-bit key; unprotected) header.d=qualcomm.com header.i=@qualcomm.com header.b="pifdwMZV"; dkim=pass (2048-bit key; unprotected) header.d=oss.qualcomm.com header.i=@oss.qualcomm.com header.b="GcySVJCA"; dkim-atps=neutral Received: from mx0a-0031df01.pphosted.com (mx0a-0031df01.pphosted.com [205.220.168.131]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 45D0962217 for ; Mon, 16 Feb 2026 20:02:17 +0100 (CET) Received: from pps.filterd (m0279865.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.18.1.11/8.18.1.11) with ESMTP id 61GC5oZc2987647 for ; Mon, 16 Feb 2026 19:02:09 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=qualcomm.com; h= cc:content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=qcppdkim1; bh=KGJwpNxvV2U wvsIFRaK7R3GhgzvleU0SLTfhWhMvPDM=; b=pifdwMZVHisoO8+2+m81C716Q1F eMDo1KAwQw4u2KZozc3yt4QJ+3t9hTbrxg0qfWgnKOViPmSkn55bJSRZvfu8AMKc 0PJwj97ZjoiuVidhnjszPnsQZ6rOhPihjiBQHsFsbymokT1B5RZ0WUznCFTGZnam DwwVLbXy6lwx19sON0CpRr313WrzEPR/KBIS7fgBrNySEZZOXNT7jgd8QbeGrX+D J/iJIJIz6josPy9VZ6mpvRuMpmw8IkaW6frCO3JMMsLNbxN8KBrRlyB7tkingA58 qpQq75Z++aTW0BDNnyPauauhkpALiXm4EcZvcvtm7u/+AR2f2Uy3wz5U0zw== Received: from mail-vk1-f197.google.com (mail-vk1-f197.google.com [209.85.221.197]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 4cbfuw340s-1 (version=TLSv1.3 cipher=TLS_AES_128_GCM_SHA256 bits=128 verify=NOT) for ; Mon, 16 Feb 2026 19:02:09 +0000 (GMT) Received: by mail-vk1-f197.google.com with SMTP id 71dfb90a1353d-5662a8e87a0so6082184e0c.1 for ; Mon, 16 Feb 2026 11:02:09 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oss.qualcomm.com; s=google; t=1771268528; x=1771873328; darn=lists.libcamera.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=KGJwpNxvV2UwvsIFRaK7R3GhgzvleU0SLTfhWhMvPDM=; b=GcySVJCA3eKDNP1Fsb1yQoj9JGpgGIhRlMp9mYT/A/OVu5/bQX/GOdEkzCaWYf/HFE +3ECL5VJY4niOSTa3kiDi+bTuo20P3WQ7E4IsSM3+3FMUx17VdjG3dwt6mOHTWZb4F2U 0Muqr2ACeFEaZp9zhGbKNVnsRy4u99TuBXx88dFyR39h7b5AJytPZvSnHqkGs/XvNO5r y5XrVcvpTTTr1mu9+8lqm3drnYKD5njjrkjpoPVuuvpo5vBcJVc5+8ny45FN7RzALGc/ T/6LddlnO+6pMJXr43knwblHlAng8FVzMbvRwWVDPsPdfQpbicCnl2sFv1Bf+QvxaV0R sgXQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1771268528; x=1771873328; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-gg:x-gm-message-state:from :to:cc:subject:date:message-id:reply-to; bh=KGJwpNxvV2UwvsIFRaK7R3GhgzvleU0SLTfhWhMvPDM=; b=B+1gGs/S8Ik7wTf10EHAf8bLeiFFYQLNx7/M0OsziwS7MJKFEtKtg3biZvM9F2n3rc cNx2T26P6UGf5yYyBc69qlH6FJC9BTtOSSMXFoIwSGLeD+OrQBIMviWNxBqwIpKyre6p Ij184Fw0upco9IdZkGkHRFmW1iAnNJxE9ZYESyO6Uxbb+neS+paHAbfNyvub3i2rBukm a0qpWD/DpP7SU5kOK043+wopx2YqoiHTKARBJK81iZJ596Kk35yjO8fLnOXPwHP+B5NI PhjpCtnzw1x2jdri6Q6ob7dKHQTLjscOCL2mtDOPn3HaryHx5KxHJjNig+cQ2O6vBgh2 3Y1Q== X-Gm-Message-State: AOJu0Yw7bfQg4Oc72Drf2Wiq68kDAmHefElHT7nbavu27gTeVb3MWEf1 +R9D6NzTXwoMLZzcigM37aoZXj0TvaDGaoebKjbDKM9X3TCDLR1Fm3/Wk1bHeZIuY5yM/9Yha7w vGN2qQX0LCZgZgaXMGvLspvxwuGL69wPtVRM4ZKrwsoZD/KuoDmr8bd++D5lKS59bFIihQtU9eA GafSD0MXw0 X-Gm-Gg: AZuq6aKSWziFe/jszY3vPzFxIJcY1nCumBVstlizzo5IGRRs3zEkqV4/2Li6OuTyKWh wtLzEpQFf8LutBT0lMrQywm/aja7lfa3lHzqL8TEbi02bbneg0TJN0nJJlo0zT2otn77eA14QWI wIUFJtaeY7MiHFktWvulcRu8eeno/BwU85jWqOfH+avBTLxP9xBd4hhN7oCFOCNyLTvi2cO1j5C YP/Y6Hsivsp6ieorkqCdHl/Ke3i8JnmYi9zmETbJAwZEoI4Cn0Kc7ImaVs9Rcph8CbCYNcgBTiH BWJ7A77mfYsfIMimkpcI4re3hi+1DWX6nl/ImK9UXIdLZiuHp1TDG7sC46OvyKnQOrQWR3UNwLY C3QuDsGdKRYZuhyY1GUfuhegYDVmJSiw17jiuopHiNhzQUH/JYNrijxMlrW/FX5GJLgoWHaVldW 1OeHEq9YQoZVa37spi8D6LAiiLyMPvUxOlahi6 X-Received: by 2002:a05:6122:2a4c:b0:567:d87:e18c with SMTP id 71dfb90a1353d-56889b8e750mr2305622e0c.9.1771268528179; Mon, 16 Feb 2026 11:02:08 -0800 (PST) X-Received: by 2002:a05:6122:2a4c:b0:567:d87:e18c with SMTP id 71dfb90a1353d-56889b8e750mr2305572e0c.9.1771268527605; Mon, 16 Feb 2026 11:02:07 -0800 (PST) Received: from shalem (2001-1c00-0c32-7800-5bfa-a036-83f0-f9ec.cable.dynamic.v6.ziggo.nl. [2001:1c00:c32:7800:5bfa:a036:83f0:f9ec]) by smtp.gmail.com with ESMTPSA id a640c23a62f3a-b8fc735e587sm276698966b.2.2026.02.16.11.02.06 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 16 Feb 2026 11:02:07 -0800 (PST) From: Hans de Goede To: libcamera-devel@lists.libcamera.org, Milan Zamazal Cc: Hans de Goede Subject: [PATCH 2/5] software_isp: debayer_cpu: Add per render thread data Date: Mon, 16 Feb 2026 20:02:01 +0100 Message-ID: <20260216190204.106922-3-johannes.goede@oss.qualcomm.com> X-Mailer: git-send-email 2.52.0 In-Reply-To: <20260216190204.106922-1-johannes.goede@oss.qualcomm.com> References: <20260216190204.106922-1-johannes.goede@oss.qualcomm.com> MIME-Version: 1.0 X-Authority-Analysis: v=2.4 cv=Jb+xbEKV c=1 sm=1 tr=0 ts=699369b1 cx=c_pps a=JIY1xp/sjQ9K5JH4t62bdg==:117 a=xqWC_Br6kY4A:10 a=HzLeVaNsDn8A:10 a=s4-Qcg_JpJYA:10 a=VkNPw1HP01LnGYTKEx00:22 a=Mpw57Om8IfrbqaoTuvik:22 a=GgsMoib0sEa3-_RKJdDe:22 a=EUspDBNiAAAA:8 a=LZmg44-WHxdkjKT3r1sA:9 a=tNoRWFLymzeba-QzToBc:22 X-Proofpoint-ORIG-GUID: Tnf95s2-LoQSF_CWipS46Gc7eyAHIkwq X-Proofpoint-GUID: Tnf95s2-LoQSF_CWipS46Gc7eyAHIkwq X-Proofpoint-Spam-Details-Enc: AW1haW4tMjYwMjE2MDE2MyBTYWx0ZWRfX9veWaIY+hMaM G50kJPbPUGs3IKJ7yu/3E4op1GiFqSQYG4b1QIJnTsY/H/10rfdkJnKsJKVccah6wp97Y1en0e7 iobp5HywP+eZ/sfDLhJym1RiROoER4iNhAlcBRArcRX8ZDd563YAZDqrV4fuNXCy6ntTJBnHC1A e6hZH/l0H+gGUKjah1lXDMI2S5tIL5rrY3pOI4BqSqG4zetMg7cVIr0iSAvfsDKlprQ6j5XgiD6 aRWDQyVP3JzU6teCQmT+UFQJxJKX7Ok7IBWzOwgxgdbZmWWL5jCEtxzKH9K8qA0QDpriSJKLiFN JfwjWXkiPAfwoqZZy3n+bL2iFjIE9UogkehHUkxiFuJc4RXxJOxzxkc9ePTVYaGeqiycyNUq/Yh 5NOrh5d3V1INAkhw/DAmGk58eNZ7PljJPMz/b63yw453oQY0XdLAmgMq2eYQZoZb47jCFmzUZqf FByQqatzTEPd8CWm2Lg== X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293, Aquarius:18.0.1121, Hydra:6.1.51, FMLib:17.12.100.49 definitions=2026-02-16_06,2026-02-16_04,2025-10-01_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 bulkscore=0 impostorscore=0 adultscore=0 suspectscore=0 spamscore=0 lowpriorityscore=0 priorityscore=1501 phishscore=0 clxscore=1015 malwarescore=0 classifier=typeunknown authscore=0 authtc= authcc= route=outbound adjust=0 reason=mlx scancount=1 engine=8.22.0-2601150000 definitions=main-2602160163 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" Add a DebayerCpuThreadData data struct and use this in the inner render loop. This contains data which needs to be separate per thread. This is a preparation patch for making DebayerCpu support multi-threading. Note this passed the DebayerCpuThreadData with a pointer rather then by reference, because passing by reference is not supported for functions passed as the thread function to std::thread(). Benchmarking on the Uno-Q with a weak CPU which is good for performance testing, shows 146-147ms per 3272x2464 frame both before and after this change, with things maybe being 0.5 ms slower after this change. Signed-off-by: Hans de Goede --- src/libcamera/software_isp/debayer_cpu.cpp | 90 ++++++++++++++-------- src/libcamera/software_isp/debayer_cpu.h | 30 +++++--- 2 files changed, 77 insertions(+), 43 deletions(-) diff --git a/src/libcamera/software_isp/debayer_cpu.cpp b/src/libcamera/software_isp/debayer_cpu.cpp index 97c1959a..e1d3c164 100644 --- a/src/libcamera/software_isp/debayer_cpu.cpp +++ b/src/libcamera/software_isp/debayer_cpu.cpp @@ -41,7 +41,7 @@ namespace libcamera { * \param[in] configuration The global configuration */ DebayerCpu::DebayerCpu(std::unique_ptr stats, const GlobalConfiguration &configuration) - : Debayer(configuration), stats_(std::move(stats)) + : Debayer(configuration), stats_(std::move(stats)), threadCount_(1) { /* * Reading from uncached buffers may be very slow. @@ -555,8 +555,9 @@ int DebayerCpu::configure(const StreamConfiguration &inputCfg, 2 * lineBufferPadding_; if (enableInputMemcpy_) { - for (unsigned int i = 0; i <= inputConfig_.patternSize.height; i++) - lineBuffers_[i].resize(lineBufferLength_); + for (unsigned int i = 0; i < threadCount_; i++) + for (unsigned int j = 0; j <= inputConfig_.patternSize.height; j++) + threadData_[i].lineBuffers[j].resize(lineBufferLength_); } return 0; @@ -600,7 +601,8 @@ DebayerCpu::strideAndFrameSize(const PixelFormat &outputFormat, const Size &size return std::make_tuple(stride, stride * size.height); } -void DebayerCpu::setupInputMemcpy(const uint8_t *linePointers[]) +void DebayerCpu::setupInputMemcpy(const uint8_t *linePointers[], + DebayerCpuThreadData *threadData) { const unsigned int patternHeight = inputConfig_.patternSize.height; @@ -608,14 +610,14 @@ void DebayerCpu::setupInputMemcpy(const uint8_t *linePointers[]) return; for (unsigned int i = 0; i < patternHeight; i++) { - memcpy(lineBuffers_[i].data(), + memcpy(threadData->lineBuffers[i].data(), linePointers[i + 1] - lineBufferPadding_, lineBufferLength_); - linePointers[i + 1] = lineBuffers_[i].data() + lineBufferPadding_; + linePointers[i + 1] = threadData->lineBuffers[i].data() + lineBufferPadding_; } /* Point lineBufferIndex_ to first unused lineBuffer */ - lineBufferIndex_ = patternHeight; + threadData->lineBufferIndex = patternHeight; } void DebayerCpu::shiftLinePointers(const uint8_t *linePointers[], const uint8_t *src) @@ -629,66 +631,78 @@ void DebayerCpu::shiftLinePointers(const uint8_t *linePointers[], const uint8_t (patternHeight / 2) * (int)inputConfig_.stride; } -void DebayerCpu::memcpyNextLine(const uint8_t *linePointers[]) +void DebayerCpu::memcpyNextLine(const uint8_t *linePointers[], + DebayerCpuThreadData *threadData) { const unsigned int patternHeight = inputConfig_.patternSize.height; if (!enableInputMemcpy_) return; - memcpy(lineBuffers_[lineBufferIndex_].data(), + memcpy(threadData->lineBuffers[threadData->lineBufferIndex].data(), linePointers[patternHeight] - lineBufferPadding_, lineBufferLength_); - linePointers[patternHeight] = lineBuffers_[lineBufferIndex_].data() + lineBufferPadding_; + linePointers[patternHeight] = threadData->lineBuffers[threadData->lineBufferIndex].data() + lineBufferPadding_; - lineBufferIndex_ = (lineBufferIndex_ + 1) % (patternHeight + 1); + threadData->lineBufferIndex = (threadData->lineBufferIndex + 1) % (patternHeight + 1); } -void DebayerCpu::process2(uint32_t frame, const uint8_t *src, uint8_t *dst) +void DebayerCpu::process2(uint32_t frame, const uint8_t *src, uint8_t *dst, + DebayerCpuThreadData *threadData) { - unsigned int yEnd = window_.height; /* Holds [0] previous- [1] current- [2] next-line */ const uint8_t *linePointers[3]; /* Adjust src to top left corner of the window */ - src += window_.y * inputConfig_.stride + window_.x * inputConfig_.bpp / 8; + src += (window_.y + threadData->yStart) * inputConfig_.stride + window_.x * inputConfig_.bpp / 8; /* [x] becomes [x - 1] after initial shiftLinePointers() call */ - if (window_.y) { + if (window_.y + threadData->yStart) { linePointers[1] = src - inputConfig_.stride; /* previous-line */ linePointers[2] = src; } else { - /* window_.y == 0, use the next line as prev line */ + /* Top line, use the next line as prev line */ linePointers[1] = src + inputConfig_.stride; linePointers[2] = src; + } + + if (window_.y == 0 && threadData->yEnd == window_.height) { /* * Last 2 lines also need special handling. * (And configure() ensures that yEnd >= 2.) */ - yEnd -= 2; + threadData->yEnd -= 2; + threadData->processLastLinesSeperately = true; + } else { + threadData->processLastLinesSeperately = false; } - setupInputMemcpy(linePointers); + setupInputMemcpy(linePointers, threadData); - for (unsigned int y = 0; y < yEnd; y += 2) { + /* + * Note y is the line-number *inside* the window, since stats_' window + * is the stats window inside/relative to the debayer window. IOW for + * single thread rendering y goes from 0 - window_.height. + */ + for (unsigned int y = threadData->yStart; y < threadData->yEnd; y += 2) { shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); + memcpyNextLine(linePointers, threadData); stats_->processLine0(frame, y, linePointers, &statsBuffer_); (this->*debayer0_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); + memcpyNextLine(linePointers, threadData); (this->*debayer1_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; } - if (window_.y == 0) { + if (threadData->processLastLinesSeperately) { shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); - stats_->processLine0(frame, yEnd, linePointers, &statsBuffer_); + memcpyNextLine(linePointers, threadData); + stats_->processLine0(frame, threadData->yEnd, linePointers, &statsBuffer_); (this->*debayer0_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; @@ -702,7 +716,8 @@ void DebayerCpu::process2(uint32_t frame, const uint8_t *src, uint8_t *dst) } } -void DebayerCpu::process4(uint32_t frame, const uint8_t *src, uint8_t *dst) +void DebayerCpu::process4(uint32_t frame, const uint8_t *src, uint8_t *dst, + DebayerCpuThreadData *threadData) { /* * This holds pointers to [0] 2-lines-up [1] 1-line-up [2] current-line @@ -711,7 +726,7 @@ void DebayerCpu::process4(uint32_t frame, const uint8_t *src, uint8_t *dst) const uint8_t *linePointers[5]; /* Adjust src to top left corner of the window */ - src += window_.y * inputConfig_.stride + window_.x * inputConfig_.bpp / 8; + src += (window_.y + threadData->yStart) * inputConfig_.stride + window_.x * inputConfig_.bpp / 8; /* [x] becomes [x - 1] after initial shiftLinePointers() call */ linePointers[1] = src - 2 * inputConfig_.stride; @@ -719,31 +734,36 @@ void DebayerCpu::process4(uint32_t frame, const uint8_t *src, uint8_t *dst) linePointers[3] = src; linePointers[4] = src + inputConfig_.stride; - setupInputMemcpy(linePointers); + setupInputMemcpy(linePointers, threadData); - for (unsigned int y = 0; y < window_.height; y += 4) { + /* + * Note y is the line-number *inside* the window, since stats_' window + * is the stats window inside/relative to the debayer window. IOW for + * single thread rendering y goes from 0 - window_.height. + */ + for (unsigned int y = threadData->yStart; y < threadData->yEnd; y += 4) { shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); + memcpyNextLine(linePointers, threadData); stats_->processLine0(frame, y, linePointers, &statsBuffer_); (this->*debayer0_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); + memcpyNextLine(linePointers, threadData); (this->*debayer1_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); + memcpyNextLine(linePointers, threadData); stats_->processLine2(frame, y, linePointers, &statsBuffer_); (this->*debayer2_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; shiftLinePointers(linePointers, src); - memcpyNextLine(linePointers); + memcpyNextLine(linePointers, threadData); (this->*debayer3_)(dst, linePointers); src += inputConfig_.stride; dst += outputConfig_.stride; @@ -868,10 +888,12 @@ void DebayerCpu::process(uint32_t frame, FrameBuffer *input, FrameBuffer *output stats_->startFrame(frame, &statsBuffer_, 1); + threadData_[0].yStart = 0; + threadData_[0].yEnd = window_.height; if (inputConfig_.patternSize.height == 2) - process2(frame, in.planes()[0].data(), out.planes()[0].data()); + process2(frame, in.planes()[0].data(), out.planes()[0].data(), &threadData_[0]); else - process4(frame, in.planes()[0].data(), out.planes()[0].data()); + process4(frame, in.planes()[0].data(), out.planes()[0].data(), &threadData_[0]); metadata.planes()[0].bytesused = out.planes()[0].size(); diff --git a/src/libcamera/software_isp/debayer_cpu.h b/src/libcamera/software_isp/debayer_cpu.h index 8abf5168..800b018c 100644 --- a/src/libcamera/software_isp/debayer_cpu.h +++ b/src/libcamera/software_isp/debayer_cpu.h @@ -74,6 +74,19 @@ private: */ using debayerFn = void (DebayerCpu::*)(uint8_t *dst, const uint8_t *src[]); + /* Max. supported Bayer pattern height is 4, debayering this requires 5 lines */ + static constexpr unsigned int kMaxLineBuffers = 5; + + /* Per render thread data */ + struct DebayerCpuThreadData { + unsigned int yStart; + unsigned int yEnd; + std::vector lineBuffers[kMaxLineBuffers]; + unsigned int lineBufferIndex; + /* Stored here to avoid causing register pressure in inner loop */ + bool processLastLinesSeperately; + }; + /* 8-bit raw bayer format */ template void debayer8_BGBG_BGR888(uint8_t *dst, const uint8_t *src[]); @@ -105,17 +118,14 @@ private: int setDebayerFunctions(PixelFormat inputFormat, PixelFormat outputFormat, bool ccmEnabled); - void setupInputMemcpy(const uint8_t *linePointers[]); + void setupInputMemcpy(const uint8_t *linePointers[], DebayerCpuThreadData *threadData); void shiftLinePointers(const uint8_t *linePointers[], const uint8_t *src); - void memcpyNextLine(const uint8_t *linePointers[]); - void process2(uint32_t frame, const uint8_t *src, uint8_t *dst); - void process4(uint32_t frame, const uint8_t *src, uint8_t *dst); + void memcpyNextLine(const uint8_t *linePointers[], DebayerCpuThreadData *threadData); + void process2(uint32_t frame, const uint8_t *src, uint8_t *dst, DebayerCpuThreadData *threadData); + void process4(uint32_t frame, const uint8_t *src, uint8_t *dst, DebayerCpuThreadData *threadData); void updateGammaTable(const DebayerParams ¶ms); void updateLookupTables(const DebayerParams ¶ms); - /* Max. supported Bayer pattern height is 4, debayering this requires 5 lines */ - static constexpr unsigned int kMaxLineBuffers = 5; - static constexpr unsigned int kRGBLookupSize = 256; static constexpr unsigned int kGammaLookupSize = 1024; struct CcmColumn { @@ -143,12 +153,14 @@ private: debayerFn debayer3_; Rectangle window_; std::unique_ptr stats_; - std::vector lineBuffers_[kMaxLineBuffers]; unsigned int lineBufferLength_; unsigned int lineBufferPadding_; - unsigned int lineBufferIndex_; unsigned int xShift_; /* Offset of 0/1 applied to window_.x */ bool enableInputMemcpy_; + + static constexpr unsigned int kMaxThreads = 4; + struct DebayerCpuThreadData threadData_[kMaxThreads]; + unsigned int threadCount_; }; } /* namespace libcamera */