[{"id":17117,"web_url":"https://patchwork.libcamera.org/comment/17117/","msgid":"<YKjaeE7mz9etdNAT@oden.dyn.berto.se>","date":"2021-05-22T10:18:32","subject":"Re: [libcamera-devel] [PATCH v4 5/5] lc-compliance: Add list and\n\tfilter parameters","submitter":{"id":5,"url":"https://patchwork.libcamera.org/api/people/5/","name":"Niklas Söderlund","email":"niklas.soderlund@ragnatech.se"},"content":"Hi Nícolas,\n\nThanks for your patch.\n\nOn 2021-05-21 10:30:54 -0300, Nícolas F. R. A. Prado wrote:\n> Add a --list parameter that lists all current tests (by mapping to\n> googletest's --gtest_list_tests).\n> \n> Add a --filter 'filterString' parameter that filters the tests to run\n> (by mapping to googletest's --gtest_filter).\n> \n> Signed-off-by: Nícolas F. R. A. Prado <nfraprado@collabora.com>\n> ---\n> No changes in v4\n> \n>  src/lc-compliance/main.cpp | 71 +++++++++++++++++++++++++++++++++++---\n>  1 file changed, 66 insertions(+), 5 deletions(-)\n> \n> diff --git a/src/lc-compliance/main.cpp b/src/lc-compliance/main.cpp\n> index 37884ff70a69..92ef9c1fa082 100644\n> --- a/src/lc-compliance/main.cpp\n> +++ b/src/lc-compliance/main.cpp\n> @@ -20,6 +20,8 @@ using namespace libcamera;\n>  \n>  enum {\n>  \tOptCamera = 'c',\n> +\tOptList = 'l',\n> +\tOptFilter = 'f',\n>  \tOptHelp = 'h',\n>  };\n>  \n> @@ -44,17 +46,25 @@ public:\n>  \t~Harness();\n>  \n>  \tint init();\n> -\tint run(int argc, char **argv);\n> +\tint run();\n> +\tint buildGtestParameters(char *arg0);\n>  \n>  private:\n>  \tvoid listCameras();\n>  \n>  \tOptionsParser::Options options_;\n>  \tstd::unique_ptr<CameraManager> cm_;\n> +\n> +\tconst std::map<std::string, std::string> gtestFlag_ = {{\"list\", \"--gtest_list_tests\"},\n> +\t\t\t\t\t\t\t       {\"filter\", \"--gtest_filter\"}};\n> +\n> +\tint gtestArgc_;\n> +\tchar **gtestArgv_;\n> +\tstd::string gtestFilterParam_;\n>  };\n>  \n>  Harness::Harness(const OptionsParser::Options &options)\n> -\t: options_(options)\n> +\t: options_(options), gtestArgv_(nullptr)\n>  {\n>  \tcm_ = std::make_unique<CameraManager>();\n>  }\n> @@ -64,6 +74,8 @@ Harness::~Harness()\n>  \tEnvironment::instance()->destroy();\n>  \n>  \tcm_->stop();\n> +\n> +\tfree(gtestArgv_);\n>  }\n>  \n>  int Harness::init()\n> @@ -77,6 +89,9 @@ int Harness::init()\n>  \t\treturn ret;\n>  \t}\n>  \n> +\tif (options_.isSet(OptList))\n> +\t\treturn 0;\n> +\n>  \tif (!options_.isSet(OptCamera)) {\n>  \t\tstd::cout << \"No camera specified, available cameras:\" << std::endl;\n>  \t\tlistCameras();\n> @@ -103,9 +118,9 @@ int Harness::init()\n>  \treturn 0;\n>  }\n>  \n> -int Harness::run(int argc, char **argv)\n> +int Harness::run()\n>  {\n> -\t::testing::InitGoogleTest(&argc, argv);\n> +\t::testing::InitGoogleTest(&gtestArgc_, gtestArgv_);\n>  \n>  \ttesting::UnitTest::GetInstance()->listeners().Append(new ThrowListener);\n>  \n> @@ -118,12 +133,54 @@ void Harness::listCameras()\n>  \t\tstd::cout << \"- \" << cam.get()->id() << std::endl;\n>  }\n>  \n> +int Harness::buildGtestParameters(char *arg0)\n> +{\n> +\tint argc = 0;\n> +\n> +\t/*\n> +\t * +2 to have space for both the 0th argument that is needed but not\n> +\t * used and the null at the end.\n> +\t */\n> +\tgtestArgv_ = (char**) malloc((gtestFlag_.size() + 2) * sizeof(char*));\n> +\tif (!gtestArgv_)\n> +\t\treturn -ENOMEM;\n> +\n> +\tgtestArgv_[argc] = arg0;\n> +\targc++;\n> +\n> +\tif (options_.isSet(OptList)) {\n> +\t\tgtestArgv_[argc] = const_cast<char*>(gtestFlag_.at(\"list\").c_str());\n> +\t\targc++;\n> +\t}\n> +\n> +\tif (options_.isSet(OptFilter)) {\n> +\t\t/*\n> +\t\t * The filter flag needs to be passed as a single parameter, in\n> +\t\t * the format --gtest_filter=filterStr\n> +\t\t */\n> +\t\tconst std::string &filter = options_[OptFilter];\n> +\t\tgtestFilterParam_ = gtestFlag_.at(\"filter\") + \"=\" + filter;\n> +\n> +\t\tgtestArgv_[argc] = const_cast<char*>(gtestFilterParam_.c_str());\n> +\t\targc++;\n> +\t}\n> +\n> +\tgtestArgv_[argc] = 0;\n> +\tgtestArgc_ = argc;\n> +\n> +\treturn 0;\n> +}\n> +\n>  static int parseOptions(int argc, char **argv, OptionsParser::Options *options)\n>  {\n>  \tOptionsParser parser;\n>  \tparser.addOption(OptCamera, OptionString,\n>  \t\t\t \"Specify which camera to operate on, by id\", \"camera\",\n>  \t\t\t ArgumentRequired, \"camera\");\n> +\tparser.addOption(OptList, OptionNone, \"List all tests and exit\", \"list\");\n> +\tparser.addOption(OptFilter, OptionString,\n> +\t\t\t \"Specify which tests to run\", \"filter\",\n> +\t\t\t ArgumentRequired, \"filter\");\n>  \tparser.addOption(OptHelp, OptionNone, \"Display this help message\",\n>  \t\t\t \"help\");\n>  \n> @@ -153,5 +210,9 @@ int main(int argc, char **argv)\n>  \tif (ret)\n>  \t\treturn ret;\n>  \n> -\treturn harness.run(argc, argv);\n> +\tret = harness.buildGtestParameters(argv[0]);\n> +\tif (ret)\n> +\t\treturn ret;\n> +\n> +\treturn harness.run();\n\nThis looks a bit odd, would it make sens to do the \nbuildGtestParameters() inside of run() instead of in main()?\n\n>  }\n> -- \n> 2.31.1\n>","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 B6E5EC3201\n\tfor <parsemail@patchwork.libcamera.org>;\n\tSat, 22 May 2021 10:18:35 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id 3C4F368918;\n\tSat, 22 May 2021 12:18:35 +0200 (CEST)","from mail-lf1-x133.google.com (mail-lf1-x133.google.com\n\t[IPv6:2a00:1450:4864:20::133])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 1877560510\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tSat, 22 May 2021 12:18:34 +0200 (CEST)","by mail-lf1-x133.google.com with SMTP id z13so33358709lft.1\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tSat, 22 May 2021 03:18:34 -0700 (PDT)","from localhost (h-155-4-209-203.A463.priv.bahnhof.se.\n\t[155.4.209.203]) by smtp.gmail.com with ESMTPSA id\n\th20sm663573lfg.103.2021.05.22.03.18.32\n\t(version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);\n\tSat, 22 May 2021 03:18:32 -0700 (PDT)"],"Authentication-Results":"lancelot.ideasonboard.com;\n\tdkim=fail reason=\"signature verification failed\" (2048-bit key;\n\tunprotected) header.d=ragnatech-se.20150623.gappssmtp.com\n\theader.i=@ragnatech-se.20150623.gappssmtp.com\n\theader.b=\"lrKIi4o8\"; dkim-atps=neutral","DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=ragnatech-se.20150623.gappssmtp.com; s=20150623;\n\th=date:from:to:cc:subject:message-id:references:mime-version\n\t:content-disposition:content-transfer-encoding:in-reply-to;\n\tbh=qrlBJU50kTXK9GxntJZfOncoBGfg43CNue0YRKPTedw=;\n\tb=lrKIi4o84HPIQRk5zg2nBRXqKtDm8Eu5LQaRgXkmJ4RabfGx3TLeREsvCl4wRygNa+\n\te4p+XZ4/MKMjHAILJ/wh/JfCx1hyUZoWcHyvFQlSgO7U+B8v+SNDA46mJ89lPkb5L5Xl\n\td4A/D2ARrjBS11a8wWVNA8bdk9lAwEsWilItBUnaY6fxKrKmC0kYIBC515oeTMPZ1+26\n\t+XYshvOCWpthKpH9YiRd8HswOnVuBX4TbHSbD+Q16ZKE6NRoCdPJXPXnTtweDvmKxPge\n\tZQQbwG2Sw49FfArIWs9+ZLJsJIQVwdpwi6c534EDgJyKflE+CQ+IIYk88g1paDDsIYFd\n\tU31Q==","X-Google-DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=1e100.net; s=20161025;\n\th=x-gm-message-state:date:from:to:cc:subject:message-id:references\n\t:mime-version:content-disposition:content-transfer-encoding\n\t:in-reply-to;\n\tbh=qrlBJU50kTXK9GxntJZfOncoBGfg43CNue0YRKPTedw=;\n\tb=sRFNuei1OhC3PnJav9klLLLN5Dqbg5Fv+9twgvGicxP28+zbrL5gxBlS1zSMZvFxyI\n\tp0nh6Qmn6EFLPwqOgrCPCU9sylihJK+t3JFwzAUKQb8LI8m13bsM566M2kfA/CmxpEfq\n\tU+4jXUxBXYKMFaGC0tJF0Q6kvSGZR3LM0JzCjDNHU7p5i+dVwXjdifiWyM1b9kf+1iBq\n\tuxQknm76lW3FYLkuqVUPoFPqivPkSBN8sJuOGnqg9X0oRM+EY2g0NxkLlgSu3Ml45okW\n\t4rBM6sjQeTvzFXba1zpNEdb3ug06fBVK74DFaUiE6HLXQoBW/35WMD8+gKdG7JuypFQx\n\tdlIQ==","X-Gm-Message-State":"AOAM532BI//s8PrXJyy8vX8L4M0I4Vsyst3lCE5LXTeDH3YaqMxD1GIJ\n\tXsJi/wKiotOzNyg46HqnhbIs68XNHmJPoQ==","X-Google-Smtp-Source":"ABdhPJwHi/xEKbdfpmsqj4o+sjtChZwKfDGJj0WSVTD1pJ8cvE9YYNvKhniTIGFuiCL3gitV+aIrag==","X-Received":"by 2002:a05:6512:3251:: with SMTP id\n\tc17mr5240090lfr.431.1621678713503; \n\tSat, 22 May 2021 03:18:33 -0700 (PDT)","Date":"Sat, 22 May 2021 12:18:32 +0200","From":"Niklas =?iso-8859-1?q?S=F6derlund?= <niklas.soderlund@ragnatech.se>","To":"=?iso-8859-1?q?N=EDcolas_F=2E_R=2E_A=2E?= Prado <nfraprado@collabora.com>","Message-ID":"<YKjaeE7mz9etdNAT@oden.dyn.berto.se>","References":"<20210521133054.274502-1-nfraprado@collabora.com>\n\t<20210521133054.274502-6-nfraprado@collabora.com>","MIME-Version":"1.0","Content-Type":"text/plain; charset=iso-8859-1","Content-Disposition":"inline","Content-Transfer-Encoding":"8bit","In-Reply-To":"<20210521133054.274502-6-nfraprado@collabora.com>","Subject":"Re: [libcamera-devel] [PATCH v4 5/5] lc-compliance: Add list and\n\tfilter parameters","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>","Cc":"libcamera-devel@lists.libcamera.org, kernel@collabora.com,\n\t=?iso-8859-1?q?Andr=E9?= Almeida <andrealmeid@collabora.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}},{"id":17213,"web_url":"https://patchwork.libcamera.org/comment/17213/","msgid":"<CBLNA8IPFOI8.E9ZSFIHCT3B9@notapiano>","date":"2021-05-24T17:17:15","subject":"Re: [libcamera-devel] [PATCH v4 5/5] lc-compliance: Add list and\n\tfilter parameters","submitter":{"id":84,"url":"https://patchwork.libcamera.org/api/people/84/","name":"Nícolas F. R. A. Prado","email":"nfraprado@collabora.com"},"content":"Hi Niklas,\n\nEm 2021-05-22 07:18, Niklas Söderlund escreveu:\n\n> Hi Nícolas,\n>\n> Thanks for your patch.\n>\n> On 2021-05-21 10:30:54 -0300, Nícolas F. R. A. Prado wrote:\n> > Add a --list parameter that lists all current tests (by mapping to\n> > googletest's --gtest_list_tests).\n> > \n> > Add a --filter 'filterString' parameter that filters the tests to run\n> > (by mapping to googletest's --gtest_filter).\n> > \n> > Signed-off-by: Nícolas F. R. A. Prado <nfraprado@collabora.com>\n> > ---\n> > No changes in v4\n> > \n> >  src/lc-compliance/main.cpp | 71 +++++++++++++++++++++++++++++++++++---\n> >  1 file changed, 66 insertions(+), 5 deletions(-)\n> > \n> > diff --git a/src/lc-compliance/main.cpp b/src/lc-compliance/main.cpp\n> > index 37884ff70a69..92ef9c1fa082 100644\n> > --- a/src/lc-compliance/main.cpp\n> > +++ b/src/lc-compliance/main.cpp\n> > @@ -20,6 +20,8 @@ using namespace libcamera;\n> >  \n> >  enum {\n> >  \tOptCamera = 'c',\n> > +\tOptList = 'l',\n> > +\tOptFilter = 'f',\n> >  \tOptHelp = 'h',\n> >  };\n> >  \n> > @@ -44,17 +46,25 @@ public:\n> >  \t~Harness();\n> >  \n> >  \tint init();\n> > -\tint run(int argc, char **argv);\n> > +\tint run();\n> > +\tint buildGtestParameters(char *arg0);\n> >  \n> >  private:\n> >  \tvoid listCameras();\n> >  \n> >  \tOptionsParser::Options options_;\n> >  \tstd::unique_ptr<CameraManager> cm_;\n> > +\n> > +\tconst std::map<std::string, std::string> gtestFlag_ = {{\"list\", \"--gtest_list_tests\"},\n> > +\t\t\t\t\t\t\t       {\"filter\", \"--gtest_filter\"}};\n> > +\n> > +\tint gtestArgc_;\n> > +\tchar **gtestArgv_;\n> > +\tstd::string gtestFilterParam_;\n> >  };\n> >  \n> >  Harness::Harness(const OptionsParser::Options &options)\n> > -\t: options_(options)\n> > +\t: options_(options), gtestArgv_(nullptr)\n> >  {\n> >  \tcm_ = std::make_unique<CameraManager>();\n> >  }\n> > @@ -64,6 +74,8 @@ Harness::~Harness()\n> >  \tEnvironment::instance()->destroy();\n> >  \n> >  \tcm_->stop();\n> > +\n> > +\tfree(gtestArgv_);\n> >  }\n> >  \n> >  int Harness::init()\n> > @@ -77,6 +89,9 @@ int Harness::init()\n> >  \t\treturn ret;\n> >  \t}\n> >  \n> > +\tif (options_.isSet(OptList))\n> > +\t\treturn 0;\n> > +\n> >  \tif (!options_.isSet(OptCamera)) {\n> >  \t\tstd::cout << \"No camera specified, available cameras:\" << std::endl;\n> >  \t\tlistCameras();\n> > @@ -103,9 +118,9 @@ int Harness::init()\n> >  \treturn 0;\n> >  }\n> >  \n> > -int Harness::run(int argc, char **argv)\n> > +int Harness::run()\n> >  {\n> > -\t::testing::InitGoogleTest(&argc, argv);\n> > +\t::testing::InitGoogleTest(&gtestArgc_, gtestArgv_);\n> >  \n> >  \ttesting::UnitTest::GetInstance()->listeners().Append(new ThrowListener);\n> >  \n> > @@ -118,12 +133,54 @@ void Harness::listCameras()\n> >  \t\tstd::cout << \"- \" << cam.get()->id() << std::endl;\n> >  }\n> >  \n> > +int Harness::buildGtestParameters(char *arg0)\n> > +{\n> > +\tint argc = 0;\n> > +\n> > +\t/*\n> > +\t * +2 to have space for both the 0th argument that is needed but not\n> > +\t * used and the null at the end.\n> > +\t */\n> > +\tgtestArgv_ = (char**) malloc((gtestFlag_.size() + 2) * sizeof(char*));\n> > +\tif (!gtestArgv_)\n> > +\t\treturn -ENOMEM;\n> > +\n> > +\tgtestArgv_[argc] = arg0;\n> > +\targc++;\n> > +\n> > +\tif (options_.isSet(OptList)) {\n> > +\t\tgtestArgv_[argc] = const_cast<char*>(gtestFlag_.at(\"list\").c_str());\n> > +\t\targc++;\n> > +\t}\n> > +\n> > +\tif (options_.isSet(OptFilter)) {\n> > +\t\t/*\n> > +\t\t * The filter flag needs to be passed as a single parameter, in\n> > +\t\t * the format --gtest_filter=filterStr\n> > +\t\t */\n> > +\t\tconst std::string &filter = options_[OptFilter];\n> > +\t\tgtestFilterParam_ = gtestFlag_.at(\"filter\") + \"=\" + filter;\n> > +\n> > +\t\tgtestArgv_[argc] = const_cast<char*>(gtestFilterParam_.c_str());\n> > +\t\targc++;\n> > +\t}\n> > +\n> > +\tgtestArgv_[argc] = 0;\n> > +\tgtestArgc_ = argc;\n> > +\n> > +\treturn 0;\n> > +}\n> > +\n> >  static int parseOptions(int argc, char **argv, OptionsParser::Options *options)\n> >  {\n> >  \tOptionsParser parser;\n> >  \tparser.addOption(OptCamera, OptionString,\n> >  \t\t\t \"Specify which camera to operate on, by id\", \"camera\",\n> >  \t\t\t ArgumentRequired, \"camera\");\n> > +\tparser.addOption(OptList, OptionNone, \"List all tests and exit\", \"list\");\n> > +\tparser.addOption(OptFilter, OptionString,\n> > +\t\t\t \"Specify which tests to run\", \"filter\",\n> > +\t\t\t ArgumentRequired, \"filter\");\n> >  \tparser.addOption(OptHelp, OptionNone, \"Display this help message\",\n> >  \t\t\t \"help\");\n> >  \n> > @@ -153,5 +210,9 @@ int main(int argc, char **argv)\n> >  \tif (ret)\n> >  \t\treturn ret;\n> >  \n> > -\treturn harness.run(argc, argv);\n> > +\tret = harness.buildGtestParameters(argv[0]);\n> > +\tif (ret)\n> > +\t\treturn ret;\n> > +\n> > +\treturn harness.run();\n>\n> This looks a bit odd, would it make sens to do the\n> buildGtestParameters() inside of run() instead of in main()?\n\nYeah, I didn't do that because I didn't want to have run() need the arg0\nparameter as well to pass to buildGtestParameters(), but I'll do it for v5.\n\nThanks,\nNícolas\n\n>\n> >  }\n> > -- \n> > 2.31.1\n> > \n>\n> --\n> Regards,\n> Niklas Söderlund\n>\n> --\n> To unsubscribe, send mail to kernel-unsubscribe@lists.collabora.co.uk.","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 A8448C3201\n\tfor <parsemail@patchwork.libcamera.org>;\n\tMon, 24 May 2021 17:17:58 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id 014D06891C;\n\tMon, 24 May 2021 19:17:58 +0200 (CEST)","from bhuna.collabora.co.uk (bhuna.collabora.co.uk\n\t[IPv6:2a00:1098:0:82:1000:25:2eeb:e3e3])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id C5C08601AA\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tMon, 24 May 2021 19:17:56 +0200 (CEST)","from [127.0.0.1] (localhost [127.0.0.1])\n\t(Authenticated sender: nfraprado) with ESMTPSA id 0E4421F41BC0"],"Mime-Version":"1.0","Content-Transfer-Encoding":"quoted-printable","Content-Type":"text/plain; charset=UTF-8","Date":"Mon, 24 May 2021 14:17:15 -0300","Message-Id":"<CBLNA8IPFOI8.E9ZSFIHCT3B9@notapiano>","From":"=?utf-8?b?TsOtY29sYXMgRi4gUi4gQS4gUHJhZG8=?= <nfraprado@collabora.com>","To":"=?utf-8?q?Niklas_S=C3=B6derlund?= <niklas.soderlund@ragnatech.se>","References":"<20210521133054.274502-1-nfraprado@collabora.com>\n\t<20210521133054.274502-6-nfraprado@collabora.com>\n\t<YKjaeE7mz9etdNAT@oden.dyn.berto.se>","In-Reply-To":"<YKjaeE7mz9etdNAT@oden.dyn.berto.se>","Subject":"Re: [libcamera-devel] [PATCH v4 5/5] lc-compliance: Add list and\n\tfilter parameters","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>","Cc":"libcamera-devel@lists.libcamera.org, kernel@collabora.com, =?utf-8?q?A?=\n\t=?utf-8?q?ndr=C3=A9_Almeida?= <andrealmeid@collabora.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}}]