Show a patch.

GET /api/1.1/patches/19851/?format=api
HTTP 200 OK
Allow: GET, PUT, PATCH, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "id": 19851,
    "url": "https://patchwork.libcamera.org/api/1.1/patches/19851/?format=api",
    "web_url": "https://patchwork.libcamera.org/patch/19851/",
    "project": {
        "id": 1,
        "url": "https://patchwork.libcamera.org/api/1.1/projects/1/?format=api",
        "name": "libcamera",
        "link_name": "libcamera",
        "list_id": "libcamera_core",
        "list_email": "libcamera-devel@lists.libcamera.org",
        "web_url": "",
        "scm_url": "",
        "webscm_url": ""
    },
    "msgid": "<20240405144729.2992219-2-paul.elder@ideasonboard.com>",
    "date": "2024-04-05T14:47:25",
    "name": "[1/5] ipa: rkisp1: agc: Read histogram weights from tuning file",
    "commit_ref": null,
    "pull_url": null,
    "state": "superseded",
    "archived": false,
    "hash": "b74998eefaedb76074afba39f1eb4b8fdb91db93",
    "submitter": {
        "id": 17,
        "url": "https://patchwork.libcamera.org/api/1.1/people/17/?format=api",
        "name": "Paul Elder",
        "email": "paul.elder@ideasonboard.com"
    },
    "delegate": null,
    "mbox": "https://patchwork.libcamera.org/patch/19851/mbox/",
    "series": [
        {
            "id": 4251,
            "url": "https://patchwork.libcamera.org/api/1.1/series/4251/?format=api",
            "web_url": "https://patchwork.libcamera.org/project/libcamera/list/?series=4251",
            "date": "2024-04-05T14:47:24",
            "name": "ipa: rkisp1: Improve AGC (plumbing)",
            "version": 1,
            "mbox": "https://patchwork.libcamera.org/series/4251/mbox/"
        }
    ],
    "comments": "https://patchwork.libcamera.org/api/patches/19851/comments/",
    "check": "pending",
    "checks": "https://patchwork.libcamera.org/api/patches/19851/checks/",
    "tags": {},
    "headers": {
        "Return-Path": "<libcamera-devel-bounces@lists.libcamera.org>",
        "X-Original-To": "parsemail@patchwork.libcamera.org",
        "Delivered-To": "parsemail@patchwork.libcamera.org",
        "Received": [
            "from lancelot.ideasonboard.com (lancelot.ideasonboard.com\n\t[92.243.16.209])\n\tby patchwork.libcamera.org (Postfix) with ESMTPS id 6D6C6C327C\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri,  5 Apr 2024 14:47:49 +0000 (UTC)",
            "from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id B5E5F61C31;\n\tFri,  5 Apr 2024 16:47:47 +0200 (CEST)",
            "from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[213.167.242.64])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id BDD1E61C2F\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri,  5 Apr 2024 16:47:46 +0200 (CEST)",
            "from pyrite.hamster-moth.ts.net (h175-177-049-156.catv02.itscom.jp\n\t[175.177.49.156])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id 0092C63B;\n\tFri,  5 Apr 2024 16:47:06 +0200 (CEST)"
        ],
        "Authentication-Results": "lancelot.ideasonboard.com; dkim=pass (1024-bit key;\n\tunprotected) header.d=ideasonboard.com header.i=@ideasonboard.com\n\theader.b=\"tB4/bgeY\"; dkim-atps=neutral",
        "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1712328428;\n\tbh=uEiZ9XUT64hX3kGNRz2krIRJMyJCutWL38psNEuR+Yo=;\n\th=From:To:Cc:Subject:Date:In-Reply-To:References:From;\n\tb=tB4/bgeYp3fMkA5kxax9Haqv7hTZym2K6VqSNtvajcOORI5aUJeBraze+NLI/lutz\n\t8J+m1hZUvBY8bLKsTgXD36tfpN7q+ZtnZrHaS6cMv+wOpm2vpSfwb6zHmqzCSbuJsX\n\tgMNdU7Fpd6uJcjAHoWcGgqRuJZVFSy7MZxaLaswU=",
        "From": "Paul Elder <paul.elder@ideasonboard.com>",
        "To": "libcamera-devel@lists.libcamera.org",
        "Cc": "Paul Elder <paul.elder@ideasonboard.com>",
        "Subject": "[PATCH 1/5] ipa: rkisp1: agc: Read histogram weights from tuning\n\tfile",
        "Date": "Fri,  5 Apr 2024 23:47:25 +0900",
        "Message-Id": "<20240405144729.2992219-2-paul.elder@ideasonboard.com>",
        "X-Mailer": "git-send-email 2.39.2",
        "In-Reply-To": "<20240405144729.2992219-1-paul.elder@ideasonboard.com>",
        "References": "<20240405144729.2992219-1-paul.elder@ideasonboard.com>",
        "MIME-Version": "1.0",
        "Content-Transfer-Encoding": "8bit",
        "X-BeenThere": "libcamera-devel@lists.libcamera.org",
        "X-Mailman-Version": "2.1.29",
        "Precedence": "list",
        "List-Id": "<libcamera-devel.lists.libcamera.org>",
        "List-Unsubscribe": "<https://lists.libcamera.org/options/libcamera-devel>,\n\t<mailto:libcamera-devel-request@lists.libcamera.org?subject=unsubscribe>",
        "List-Archive": "<https://lists.libcamera.org/pipermail/libcamera-devel/>",
        "List-Post": "<mailto:libcamera-devel@lists.libcamera.org>",
        "List-Help": "<mailto:libcamera-devel-request@lists.libcamera.org?subject=help>",
        "List-Subscribe": "<https://lists.libcamera.org/listinfo/libcamera-devel>,\n\t<mailto:libcamera-devel-request@lists.libcamera.org?subject=subscribe>",
        "Errors-To": "libcamera-devel-bounces@lists.libcamera.org",
        "Sender": "\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"
    },
    "content": "Add support to the rkisp1 AGC to read histogram weights from the tuning\nfile. As controls for selecting the metering mode are not yet supported,\nfor now hardcode the matrix metering mode, which is the same as what the\nAGC previously hardcoded.\n\nSigned-off-by: Paul Elder <paul.elder@ideasonboard.com>\n---\n src/ipa/rkisp1/algorithms/agc.cpp | 80 +++++++++++++++++++++++++++++--\n src/ipa/rkisp1/algorithms/agc.h   |  6 +++\n 2 files changed, 83 insertions(+), 3 deletions(-)",
    "diff": "diff --git a/src/ipa/rkisp1/algorithms/agc.cpp b/src/ipa/rkisp1/algorithms/agc.cpp\nindex 1cd977a0..fd47ba4e 100644\n--- a/src/ipa/rkisp1/algorithms/agc.cpp\n+++ b/src/ipa/rkisp1/algorithms/agc.cpp\n@@ -17,6 +17,8 @@\n #include <libcamera/control_ids.h>\n #include <libcamera/ipa/core_ipa_interface.h>\n \n+#include \"libcamera/internal/yaml_parser.h\"\n+\n #include \"libipa/histogram.h\"\n \n /**\n@@ -42,6 +44,62 @@ static constexpr double kMinAnalogueGain = 1.0;\n /* \\todo Honour the FrameDurationLimits control instead of hardcoding a limit */\n static constexpr utils::Duration kMaxShutterSpeed = 60ms;\n \n+int Agc::parseMeteringModes(IPAContext &context, const YamlObject &tuningData,\n+\t\t\t    const char *prop)\n+{\n+\tconst YamlObject &yamlMeteringModes = tuningData[prop];\n+\tif (!yamlMeteringModes.isDictionary()) {\n+\t\tLOG(RkISP1Agc, Error)\n+\t\t\t<< \"'\" << prop << \"' parameter not found in tuning file\";\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tfor (const auto &[key, value] : yamlMeteringModes.asDict()) {\n+\t\tif (controls::AeMeteringModeNameValueMap.find(key) ==\n+\t\t    controls::AeMeteringModeNameValueMap.end()) {\n+\t\t\tLOG(RkISP1Agc, Warning)\n+\t\t\t\t<< \"Skipping unknown metering mode '\" << key << \"'\";\n+\t\t\tcontinue;\n+\t\t}\n+\n+\t\tstd::vector<uint8_t> weights =\n+\t\t\tvalue.getList<uint8_t>().value_or(std::vector<uint8_t>{});\n+\t\tif (weights.size() != context.hw->numHistogramWeights) {\n+\t\t\tLOG(RkISP1Agc, Error)\n+\t\t\t\t<< \"Invalid '\" << key << \"' values: expected \"\n+\t\t\t\t<< context.hw->numHistogramWeights\n+\t\t\t\t<< \" elements, got \" << weights.size();\n+\t\t\treturn -ENODATA;\n+\t\t}\n+\n+\t\tmeteringModes_[controls::AeMeteringModeNameValueMap.at(key)] = weights;\n+\t}\n+\n+\treturn 0;\n+}\n+\n+uint8_t Agc::predivider(Size &size)\n+{\n+\tstatic const std::vector<std::pair<unsigned int, unsigned int>>\n+\t\tpixelCountThresholds = {\n+\t\t\t{  640 *  480,  3 },\n+\t\t\t{  800 *  600,  4 },\n+\t\t\t{ 1024 *  768,  5 },\n+\t\t\t{ 1280 *  960,  6 },\n+\t\t\t{ 1600 * 1200,  8 },\n+\t\t\t{ 2048 * 1536, 10 },\n+\t\t\t{ 2600 * 1950, 12 },\n+\t\t\t{ 4096 * 3072, 16 },\n+\t\t};\n+\n+\tunsigned long pixels = size.width * size.height;\n+\tfor (auto &pair : pixelCountThresholds)\n+\t\tif (pixels < pair.first)\n+\t\t\treturn pair.second;\n+\n+\treturn 24;\n+}\n+\n Agc::Agc()\n {\n \tsupportsRaw_ = true;\n@@ -72,6 +130,10 @@ int Agc::init(IPAContext &context, const YamlObject &tuningData)\n \tif (ret)\n \t\treturn ret;\n \n+\tret = parseMeteringModes(context, tuningData, \"AeMeteringMode\");\n+\tif (ret)\n+\t\treturn ret;\n+\n \tcontext.ctrlMap.merge(controls());\n \n \treturn 0;\n@@ -177,6 +239,7 @@ void Agc::prepare(IPAContext &context, const uint32_t frame,\n \t\tframeContext.agc.gain = context.activeState.agc.automatic.gain;\n \t}\n \n+\t/* \\todo Remove this when we can set the below with controls */\n \tif (frame > 0)\n \t\treturn;\n \n@@ -195,14 +258,25 @@ void Agc::prepare(IPAContext &context, const uint32_t frame,\n \tparams->meas.hst_config.meas_window = context.configuration.agc.measureWindow;\n \t/* Produce the luminance histogram. */\n \tparams->meas.hst_config.mode = RKISP1_CIF_ISP_HISTOGRAM_MODE_Y_HISTOGRAM;\n+\n \t/* Set an average weighted histogram. */\n \tSpan<uint8_t> weights{\n \t\tparams->meas.hst_config.hist_weight,\n \t\tcontext.hw->numHistogramWeights\n \t};\n-\tstd::fill(weights.begin(), weights.end(), 1);\n-\t/* Step size can't be less than 3. */\n-\tparams->meas.hst_config.histogram_predivider = 4;\n+\t/* \\todo Get this from control */\n+\tstd::vector<uint8_t> &modeWeights = meteringModes_.at(controls::MeteringMatrix);\n+\tstd::copy(modeWeights.begin(), modeWeights.end(), weights.begin());\n+\n+\tstd::stringstream str;\n+\tstr << \"Histogram weights : \";\n+\tfor (size_t i = 0; i < context.hw->numHistogramWeights; i++)\n+\t\tstr << (int)params->meas.hst_config.hist_weight[i] << \" \";\n+\tLOG(RkISP1Agc, Debug) << str.str();\n+\n+\t/* \\todo Add a control for this? */\n+\tparams->meas.hst_config.histogram_predivider =\n+\t\tpredivider(context.configuration.sensor.size);\n \n \t/* Update the configuration for histogram. */\n \tparams->module_cfg_update |= RKISP1_CIF_ISP_MODULE_HST;\ndiff --git a/src/ipa/rkisp1/algorithms/agc.h b/src/ipa/rkisp1/algorithms/agc.h\nindex 311d4e94..43e3d5b2 100644\n--- a/src/ipa/rkisp1/algorithms/agc.h\n+++ b/src/ipa/rkisp1/algorithms/agc.h\n@@ -44,6 +44,10 @@ public:\n \t\t     ControlList &metadata) override;\n \n private:\n+\tint parseMeteringModes(IPAContext &context, const YamlObject &tuningData,\n+\t\t\t       const char *prop);\n+\tuint8_t predivider(Size &size);\n+\n \tvoid fillMetadata(IPAContext &context, IPAFrameContext &frameContext,\n \t\t\t  ControlList &metadata);\n \tvoid parseStatistics(const rkisp1_stat_buffer *stats,\n@@ -52,6 +56,8 @@ private:\n \n \tHistogram hist_;\n \tSpan<const uint8_t> expMeans_;\n+\n+\tstd::map<int32_t, std::vector<uint8_t>> meteringModes_;\n };\n \n } /* namespace ipa::rkisp1::algorithms */\n",
    "prefixes": [
        "1/5"
    ]
}