diff options
author | Naushir Patuck <naush@raspberrypi.com> | 2023-05-03 13:20:27 +0100 |
---|---|---|
committer | Laurent Pinchart <laurent.pinchart@ideasonboard.com> | 2023-05-04 20:47:40 +0300 |
commit | 726e9274ea95fa46352556d340c5793a8da51fcd (patch) | |
tree | 80f6adcdbf744f9317e09eff3e80c602b384a753 /src/ipa/raspberrypi/controller/rpi/ccm.cpp | |
parent | 46aefed208fef4bc8d6f6e8882b92b9af710a60b (diff) |
pipeline: ipa: raspberrypi: Refactor and move the Raspberry Pi code
Split the Raspberry Pi pipeline handler and IPA source code into common
and VC4/BCM2835 specific file structures.
For the pipeline handler, the common code files now live in
src/libcamera/pipeline/rpi/common/
and the VC4-specific files in src/libcamera/pipeline/rpi/vc4/.
For the IPA, the common code files now live in
src/ipa/rpi/{cam_helper,controller}/
and the vc4 specific files in src/ipa/rpi/vc4/. With this change, the
camera tuning files are now installed under share/libcamera/ipa/rpi/vc4/.
To build the pipeline and IPA, the meson configuration options have now
changed from "raspberrypi" to "rpi/vc4":
meson setup build -Dipas=rpi/vc4 -Dpipelines=rpi/vc4
Signed-off-by: Naushir Patuck <naush@raspberrypi.com>
Reviewed-by: Jacopo Mondi <jacopo.mondi@ideasonboard.com>
Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Diffstat (limited to 'src/ipa/raspberrypi/controller/rpi/ccm.cpp')
-rw-r--r-- | src/ipa/raspberrypi/controller/rpi/ccm.cpp | 199 |
1 files changed, 0 insertions, 199 deletions
diff --git a/src/ipa/raspberrypi/controller/rpi/ccm.cpp b/src/ipa/raspberrypi/controller/rpi/ccm.cpp deleted file mode 100644 index 2e2e6664..00000000 --- a/src/ipa/raspberrypi/controller/rpi/ccm.cpp +++ /dev/null @@ -1,199 +0,0 @@ -/* SPDX-License-Identifier: BSD-2-Clause */ -/* - * Copyright (C) 2019, Raspberry Pi Ltd - * - * ccm.cpp - CCM (colour correction matrix) control algorithm - */ - -#include <libcamera/base/log.h> - -#include "../awb_status.h" -#include "../ccm_status.h" -#include "../lux_status.h" -#include "../metadata.h" - -#include "ccm.h" - -using namespace RPiController; -using namespace libcamera; - -LOG_DEFINE_CATEGORY(RPiCcm) - -/* - * This algorithm selects a CCM (Colour Correction Matrix) according to the - * colour temperature estimated by AWB (interpolating between known matricies as - * necessary). Additionally the amount of colour saturation can be controlled - * both according to the current estimated lux level and according to a - * saturation setting that is exposed to applications. - */ - -#define NAME "rpi.ccm" - -Matrix::Matrix() -{ - memset(m, 0, sizeof(m)); -} -Matrix::Matrix(double m0, double m1, double m2, double m3, double m4, double m5, - double m6, double m7, double m8) -{ - m[0][0] = m0, m[0][1] = m1, m[0][2] = m2, m[1][0] = m3, m[1][1] = m4, - m[1][2] = m5, m[2][0] = m6, m[2][1] = m7, m[2][2] = m8; -} -int Matrix::read(const libcamera::YamlObject ¶ms) -{ - double *ptr = (double *)m; - - if (params.size() != 9) { - LOG(RPiCcm, Error) << "Wrong number of values in CCM"; - return -EINVAL; - } - - for (const auto ¶m : params.asList()) { - auto value = param.get<double>(); - if (!value) - return -EINVAL; - *ptr++ = *value; - } - - return 0; -} - -Ccm::Ccm(Controller *controller) - : CcmAlgorithm(controller), saturation_(1.0) {} - -char const *Ccm::name() const -{ - return NAME; -} - -int Ccm::read(const libcamera::YamlObject ¶ms) -{ - int ret; - - if (params.contains("saturation")) { - ret = config_.saturation.read(params["saturation"]); - if (ret) - return ret; - } - - for (auto &p : params["ccms"].asList()) { - auto value = p["ct"].get<double>(); - if (!value) - return -EINVAL; - - CtCcm ctCcm; - ctCcm.ct = *value; - ret = ctCcm.ccm.read(p["ccm"]); - if (ret) - return ret; - - if (!config_.ccms.empty() && ctCcm.ct <= config_.ccms.back().ct) { - LOG(RPiCcm, Error) - << "CCM not in increasing colour temperature order"; - return -EINVAL; - } - - config_.ccms.push_back(std::move(ctCcm)); - } - - if (config_.ccms.empty()) { - LOG(RPiCcm, Error) << "No CCMs specified"; - return -EINVAL; - } - - return 0; -} - -void Ccm::setSaturation(double saturation) -{ - saturation_ = saturation; -} - -void Ccm::initialise() -{ -} - -template<typename T> -static bool getLocked(Metadata *metadata, std::string const &tag, T &value) -{ - T *ptr = metadata->getLocked<T>(tag); - if (ptr == nullptr) - return false; - value = *ptr; - return true; -} - -Matrix calculateCcm(std::vector<CtCcm> const &ccms, double ct) -{ - if (ct <= ccms.front().ct) - return ccms.front().ccm; - else if (ct >= ccms.back().ct) - return ccms.back().ccm; - else { - int i = 0; - for (; ct > ccms[i].ct; i++) - ; - double lambda = - (ct - ccms[i - 1].ct) / (ccms[i].ct - ccms[i - 1].ct); - return lambda * ccms[i].ccm + (1.0 - lambda) * ccms[i - 1].ccm; - } -} - -Matrix applySaturation(Matrix const &ccm, double saturation) -{ - Matrix RGB2Y(0.299, 0.587, 0.114, -0.169, -0.331, 0.500, 0.500, -0.419, - -0.081); - Matrix Y2RGB(1.000, 0.000, 1.402, 1.000, -0.345, -0.714, 1.000, 1.771, - 0.000); - Matrix S(1, 0, 0, 0, saturation, 0, 0, 0, saturation); - return Y2RGB * S * RGB2Y * ccm; -} - -void Ccm::prepare(Metadata *imageMetadata) -{ - bool awbOk = false, luxOk = false; - struct AwbStatus awb = {}; - awb.temperatureK = 4000; /* in case no metadata */ - struct LuxStatus lux = {}; - lux.lux = 400; /* in case no metadata */ - { - /* grab mutex just once to get everything */ - std::lock_guard<Metadata> lock(*imageMetadata); - awbOk = getLocked(imageMetadata, "awb.status", awb); - luxOk = getLocked(imageMetadata, "lux.status", lux); - } - if (!awbOk) - LOG(RPiCcm, Warning) << "no colour temperature found"; - if (!luxOk) - LOG(RPiCcm, Warning) << "no lux value found"; - Matrix ccm = calculateCcm(config_.ccms, awb.temperatureK); - double saturation = saturation_; - struct CcmStatus ccmStatus; - ccmStatus.saturation = saturation; - if (!config_.saturation.empty()) - saturation *= config_.saturation.eval( - config_.saturation.domain().clip(lux.lux)); - ccm = applySaturation(ccm, saturation); - for (int j = 0; j < 3; j++) - for (int i = 0; i < 3; i++) - ccmStatus.matrix[j * 3 + i] = - std::max(-8.0, std::min(7.9999, ccm.m[j][i])); - LOG(RPiCcm, Debug) - << "colour temperature " << awb.temperatureK << "K"; - LOG(RPiCcm, Debug) - << "CCM: " << ccmStatus.matrix[0] << " " << ccmStatus.matrix[1] - << " " << ccmStatus.matrix[2] << " " - << ccmStatus.matrix[3] << " " << ccmStatus.matrix[4] - << " " << ccmStatus.matrix[5] << " " - << ccmStatus.matrix[6] << " " << ccmStatus.matrix[7] - << " " << ccmStatus.matrix[8]; - imageMetadata->set("ccm.status", ccmStatus); -} - -/* Register algorithm with the system. */ -static Algorithm *create(Controller *controller) -{ - return (Algorithm *)new Ccm(controller); - ; -} -static RegisterAlgorithm reg(NAME, &create); |