[{"id":27945,"web_url":"https://patchwork.libcamera.org/comment/27945/","msgid":"<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>","date":"2023-10-12T08:29:47","subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","submitter":{"id":4,"url":"https://patchwork.libcamera.org/api/people/4/","name":"Kieran Bingham","email":"kieran.bingham@ideasonboard.com"},"content":"Hi David,\n\nQuoting David Plowman via libcamera-devel (2023-10-11 15:02:38)\n> We provide access to the various fields of the new SensorConfiguration\n> class. The class also needs a constructor so that Python applications\n> can make one and put it into the CameraConfiguration.\n> \n> Signed-off-by: David Plowman <david.plowman@raspberrypi.com>\n> ---\n>  src/py/libcamera/py_main.cpp | 36 ++++++++++++++++++++++++++++++++++++\n>  1 file changed, 36 insertions(+)\n> \n> diff --git a/src/py/libcamera/py_main.cpp b/src/py/libcamera/py_main.cpp\n> index 01fb15a9..d2ce3722 100644\n> --- a/src/py/libcamera/py_main.cpp\n> +++ b/src/py/libcamera/py_main.cpp\n> @@ -112,6 +112,7 @@ PYBIND11_MODULE(_libcamera, m)\n>  \n>         auto pyCameraManager = py::class_<PyCameraManager, std::shared_ptr<PyCameraManager>>(m, \"CameraManager\");\n>         auto pyCamera = py::class_<Camera, PyCameraSmartPtr<Camera>>(m, \"Camera\");\n> +       auto pySensorConfiguration = py::class_<SensorConfiguration>(m, \"SensorConfiguration\");\n>         auto pyCameraConfiguration = py::class_<CameraConfiguration>(m, \"CameraConfiguration\");\n>         auto pyCameraConfigurationStatus = py::enum_<CameraConfiguration::Status>(pyCameraConfiguration, \"Status\");\n>         auto pyStreamConfiguration = py::class_<StreamConfiguration>(m, \"StreamConfiguration\");\n> @@ -281,6 +282,40 @@ PYBIND11_MODULE(_libcamera, m)\n>                         return ret;\n>                 });\n>  \n> +       pySensorConfiguration\n> +               .def(py::init<>())\n> +               .def_readwrite(\"bit_depth\", &SensorConfiguration::bitDepth)\n> +               .def_readwrite(\"analog_crop\", &SensorConfiguration::analogCrop)\n> +               .def_property(\n> +                       \"binning\",\n> +                       [](SensorConfiguration &self) {\n> +                               return py::make_tuple(self.binning.binX, self.binning.binY);\n> +                       },\n> +                       [](SensorConfiguration &self, py::object value) {\n> +                               auto vec = value.cast<std::vector<unsigned int>>();\n> +                               if (vec.size() != 2)\n> +                                       throw std::runtime_error(\"binning requires iterable of 2 values\");\n> +                               self.binning.binX = vec[0];\n> +                               self.binning.binY = vec[1];\n\nThis seems reasonable to me. Partially filling in either of binning or\nskipping would be invalid.\n\nThanks for filling in the rest of the logic:\n\nReviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com>\n\nTomi - Are you happy with this?\n\n\n\n> +                       })\n> +               .def_property(\n> +                       \"skipping\",\n> +                       [](SensorConfiguration &self) {\n> +                               return py::make_tuple(self.skipping.xOddInc, self.skipping.xEvenInc,\n> +                                                     self.skipping.yOddInc, self.skipping.yEvenInc);\n> +                       },\n> +                       [](SensorConfiguration &self, py::object value) {\n> +                               auto vec = value.cast<std::vector<unsigned int>>();\n> +                               if (vec.size() != 4)\n> +                                       throw std::runtime_error(\"skipping requires iterable of 4 values\");\n> +                               self.skipping.xOddInc = vec[0];\n> +                               self.skipping.xEvenInc = vec[1];\n> +                               self.skipping.yOddInc = vec[2];\n> +                               self.skipping.yEvenInc = vec[3];\n> +                       })\n> +               .def_readwrite(\"output_size\", &SensorConfiguration::outputSize)\n> +               .def(\"is_valid\", &SensorConfiguration::isValid);\n> +\n>         pyCameraConfiguration\n>                 .def(\"__iter__\", [](CameraConfiguration &self) {\n>                         return py::make_iterator<py::return_value_policy::reference_internal>(self);\n> @@ -293,6 +328,7 @@ PYBIND11_MODULE(_libcamera, m)\n>                      py::return_value_policy::reference_internal)\n>                 .def_property_readonly(\"size\", &CameraConfiguration::size)\n>                 .def_property_readonly(\"empty\", &CameraConfiguration::empty)\n> +               .def_readwrite(\"sensor_config\", &CameraConfiguration::sensorConfig)\n>                 .def_readwrite(\"transform\", &CameraConfiguration::transform);\n>  \n>         pyCameraConfigurationStatus\n> -- \n> 2.39.2\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 D7244C3272\n\tfor <parsemail@patchwork.libcamera.org>;\n\tThu, 12 Oct 2023 08:29:52 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id 26B8E62980;\n\tThu, 12 Oct 2023 10:29:52 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[213.167.242.64])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 94EE86297B\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tThu, 12 Oct 2023 10:29:50 +0200 (CEST)","from pendragon.ideasonboard.com\n\t(aztw-30-b2-v4wan-166917-cust845.vm26.cable.virginm.net\n\t[82.37.23.78])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id 6C292583;\n\tThu, 12 Oct 2023 10:29:47 +0200 (CEST)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1697099392;\n\tbh=FemBGvNLqHOmXl9ioWiCQLLukdVoDrCLGNf8TV8rMxc=;\n\th=In-Reply-To:References:To:Date:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:\n\tFrom;\n\tb=tApWAEHSRgtWdra7CysWj07jtgxL/FaW3dOk+I9/mjsv1OqgFd+d4CCq38rGcOFuo\n\tJmg4ZZ4/fLS54tNsOVn30zosKD+dauQJswf1Ng4V9sK3TtC/fkLFq8UQur0dermxoU\n\tQd6R694xns4qNX/Ey1aVL98tHnbnw7MKvIyjnjc3w+Vzz+GFTRAP9vhgqfsLU4+i2J\n\txMZXH5peN031rCJtMnSaL7YfG0EUexLAfmTfRencGSU/hTZVO960g3d5svufXz0coX\n\tX7iPtx4HwwrpA1MZ3JudgB/XYqU85yCrbmdP7yuosNQeoQ3uHqQBYS48HAKjR/w5av\n\trESQ3/6p4uCIw==","v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1697099387;\n\tbh=FemBGvNLqHOmXl9ioWiCQLLukdVoDrCLGNf8TV8rMxc=;\n\th=In-Reply-To:References:Subject:From:To:Date:From;\n\tb=ta6R4O7Y+fYA5qcj27X1dwZYvjZwaOc1Gh9yB/m4mgGP0tF3qcgvKewarJQEsTwEE\n\tcYnvOoPwXnqtmispn7YSi3gH7AXCYRMor/MEz7l7pgDSDVSgw0wAzd16WtobZS8ckf\n\tA+cREMsUelIxBEQOQrtCeIjj4yxTrsGvH4rVH9HA="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (1024-bit key; \n\tunprotected) header.d=ideasonboard.com\n\theader.i=@ideasonboard.com\n\theader.b=\"ta6R4O7Y\"; dkim-atps=neutral","Content-Type":"text/plain; charset=\"utf-8\"","MIME-Version":"1.0","Content-Transfer-Encoding":"quoted-printable","In-Reply-To":"<20231011140238.39058-1-david.plowman@raspberrypi.com>","References":"<20231011140238.39058-1-david.plowman@raspberrypi.com>","To":"David Plowman <david.plowman@raspberrypi.com>,\n\tlibcamera-devel@lists.libcamera.org","Date":"Thu, 12 Oct 2023 09:29:47 +0100","Message-ID":"<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>","User-Agent":"alot/0.10","Subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","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>","From":"Kieran Bingham via libcamera-devel\n\t<libcamera-devel@lists.libcamera.org>","Reply-To":"Kieran Bingham <kieran.bingham@ideasonboard.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}},{"id":28010,"web_url":"https://patchwork.libcamera.org/comment/28010/","msgid":"<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>","date":"2023-10-20T07:51:08","subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","submitter":{"id":109,"url":"https://patchwork.libcamera.org/api/people/109/","name":"Tomi Valkeinen","email":"tomi.valkeinen@ideasonboard.com"},"content":"On 12/10/2023 11:29, Kieran Bingham via libcamera-devel wrote:\n> Hi David,\n> \n> Quoting David Plowman via libcamera-devel (2023-10-11 15:02:38)\n>> We provide access to the various fields of the new SensorConfiguration\n>> class. The class also needs a constructor so that Python applications\n>> can make one and put it into the CameraConfiguration.\n>>\n>> Signed-off-by: David Plowman <david.plowman@raspberrypi.com>\n>> ---\n>>   src/py/libcamera/py_main.cpp | 36 ++++++++++++++++++++++++++++++++++++\n>>   1 file changed, 36 insertions(+)\n>>\n>> diff --git a/src/py/libcamera/py_main.cpp b/src/py/libcamera/py_main.cpp\n>> index 01fb15a9..d2ce3722 100644\n>> --- a/src/py/libcamera/py_main.cpp\n>> +++ b/src/py/libcamera/py_main.cpp\n>> @@ -112,6 +112,7 @@ PYBIND11_MODULE(_libcamera, m)\n>>   \n>>          auto pyCameraManager = py::class_<PyCameraManager, std::shared_ptr<PyCameraManager>>(m, \"CameraManager\");\n>>          auto pyCamera = py::class_<Camera, PyCameraSmartPtr<Camera>>(m, \"Camera\");\n>> +       auto pySensorConfiguration = py::class_<SensorConfiguration>(m, \"SensorConfiguration\");\n>>          auto pyCameraConfiguration = py::class_<CameraConfiguration>(m, \"CameraConfiguration\");\n>>          auto pyCameraConfigurationStatus = py::enum_<CameraConfiguration::Status>(pyCameraConfiguration, \"Status\");\n>>          auto pyStreamConfiguration = py::class_<StreamConfiguration>(m, \"StreamConfiguration\");\n>> @@ -281,6 +282,40 @@ PYBIND11_MODULE(_libcamera, m)\n>>                          return ret;\n>>                  });\n>>   \n>> +       pySensorConfiguration\n>> +               .def(py::init<>())\n>> +               .def_readwrite(\"bit_depth\", &SensorConfiguration::bitDepth)\n>> +               .def_readwrite(\"analog_crop\", &SensorConfiguration::analogCrop)\n>> +               .def_property(\n>> +                       \"binning\",\n>> +                       [](SensorConfiguration &self) {\n>> +                               return py::make_tuple(self.binning.binX, self.binning.binY);\n>> +                       },\n>> +                       [](SensorConfiguration &self, py::object value) {\n>> +                               auto vec = value.cast<std::vector<unsigned int>>();\n>> +                               if (vec.size() != 2)\n>> +                                       throw std::runtime_error(\"binning requires iterable of 2 values\");\n>> +                               self.binning.binX = vec[0];\n>> +                               self.binning.binY = vec[1];\n> \n> This seems reasonable to me. Partially filling in either of binning or\n> skipping would be invalid.\n> \n> Thanks for filling in the rest of the logic:\n> \n> Reviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com>\n> \n> Tomi - Are you happy with this?\n\nI think it's simpler and better to do:\n\n.def_property(\n\t\"binning\",\n\t[](SensorConfiguration &self) {\n\t\treturn std::make_tuple(self.binning.binX, self.binning.binY);\n\t},\n\t[](SensorConfiguration &self, std::tuple<uint32_t, uint32_t> value) {\n\t\tself.binning.binX = std::get<0>(value);\n\t\tself.binning.binY = std::get<1>(value);\n\t})\n\n  Tomi\n\n\n> \n> \n> \n>> +                       })\n>> +               .def_property(\n>> +                       \"skipping\",\n>> +                       [](SensorConfiguration &self) {\n>> +                               return py::make_tuple(self.skipping.xOddInc, self.skipping.xEvenInc,\n>> +                                                     self.skipping.yOddInc, self.skipping.yEvenInc);\n>> +                       },\n>> +                       [](SensorConfiguration &self, py::object value) {\n>> +                               auto vec = value.cast<std::vector<unsigned int>>();\n>> +                               if (vec.size() != 4)\n>> +                                       throw std::runtime_error(\"skipping requires iterable of 4 values\");\n>> +                               self.skipping.xOddInc = vec[0];\n>> +                               self.skipping.xEvenInc = vec[1];\n>> +                               self.skipping.yOddInc = vec[2];\n>> +                               self.skipping.yEvenInc = vec[3];\n>> +                       })\n>> +               .def_readwrite(\"output_size\", &SensorConfiguration::outputSize)\n>> +               .def(\"is_valid\", &SensorConfiguration::isValid);\n>> +\n>>          pyCameraConfiguration\n>>                  .def(\"__iter__\", [](CameraConfiguration &self) {\n>>                          return py::make_iterator<py::return_value_policy::reference_internal>(self);\n>> @@ -293,6 +328,7 @@ PYBIND11_MODULE(_libcamera, m)\n>>                       py::return_value_policy::reference_internal)\n>>                  .def_property_readonly(\"size\", &CameraConfiguration::size)\n>>                  .def_property_readonly(\"empty\", &CameraConfiguration::empty)\n>> +               .def_readwrite(\"sensor_config\", &CameraConfiguration::sensorConfig)\n>>                  .def_readwrite(\"transform\", &CameraConfiguration::transform);\n>>   \n>>          pyCameraConfigurationStatus\n>> -- \n>> 2.39.2\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 1E478C3272\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri, 20 Oct 2023 07:51:14 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id 307976297F;\n\tFri, 20 Oct 2023 09:51:13 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[213.167.242.64])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 8C3B861DCF\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 20 Oct 2023 09:51:11 +0200 (CEST)","from [192.168.88.20] (91-158-145-56.elisa-laajakaista.fi\n\t[91.158.145.56])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id B3036B2A;\n\tFri, 20 Oct 2023 09:51:02 +0200 (CEST)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1697788273;\n\tbh=b4xK6s3dOlS1IADCJAZPLHsZRA9UTaCJkv2u8aUho70=;\n\th=Date:To:References:In-Reply-To:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:\n\tFrom;\n\tb=r7txx1UUnU3hQoZy24Z2hu+KCkptS66vvoclqfNvezoxKbmrjz+ULrFydGtNFjPI0\n\tDki3tcyAZ8JD+VXbPLTIDjpYOJAT21eEkGdJaUI8hgdZiFOkT8H45A0bEf/WYL39WC\n\t0zlXzxvwvInbsNmvfOg9fWwoYJn5fN2n602uxaoDSWYddBTCpxWZ1ftPG1RrlMqwCZ\n\tEQetwMo5bvTa2impIHijTIahYoU9W3ksC+Yw3w10PKjhawVXlPq87mytX1AMjJEsu1\n\tsgCBIp3IRrN+DK6e9HS0vdXRdmdVCC6Lh4EdXyyapsWA9pRvF9jvtDKICi1gevIvGA\n\tf1duNBNdbxGHg==","v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1697788262;\n\tbh=b4xK6s3dOlS1IADCJAZPLHsZRA9UTaCJkv2u8aUho70=;\n\th=Date:Subject:To:References:From:In-Reply-To:From;\n\tb=vGaXB40RkmOZfxa/Zq4tj+fST5OtYvts8EoHcyQhiyd0oqzF/GpQwhhW4W1Dl6DnL\n\txVCPDiSLSMO/G0Ju5MoF4Ns827sq/BESwExRXbGTpXv18z4cl7x0lu1VTkv61VEOsc\n\tUQytVNRxvuZK0/14qFSLnQnA8KFzEylc3q82lkqQ="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (1024-bit key; \n\tunprotected) header.d=ideasonboard.com\n\theader.i=@ideasonboard.com\n\theader.b=\"vGaXB40R\"; dkim-atps=neutral","Message-ID":"<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>","Date":"Fri, 20 Oct 2023 10:51:08 +0300","MIME-Version":"1.0","User-Agent":"Mozilla Thunderbird","To":"Kieran Bingham <kieran.bingham@ideasonboard.com>,\n\tDavid Plowman <david.plowman@raspberrypi.com>,\n\tlibcamera-devel@lists.libcamera.org","References":"<20231011140238.39058-1-david.plowman@raspberrypi.com>\n\t<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>","Content-Language":"en-US","Autocrypt":"addr=tomi.valkeinen@ideasonboard.com; keydata=\n\t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","In-Reply-To":"<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>","Content-Type":"text/plain; charset=UTF-8; format=flowed","Content-Transfer-Encoding":"7bit","Subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","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>","From":"Tomi Valkeinen via libcamera-devel\n\t<libcamera-devel@lists.libcamera.org>","Reply-To":"Tomi Valkeinen <tomi.valkeinen@ideasonboard.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}},{"id":28011,"web_url":"https://patchwork.libcamera.org/comment/28011/","msgid":"<CAHW6GYL5gzZqRkpCSwYisLWAzY6Wcxb9jAGBAhtoroA4YejZGw@mail.gmail.com>","date":"2023-10-20T08:17:08","subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","submitter":{"id":42,"url":"https://patchwork.libcamera.org/api/people/42/","name":"David Plowman","email":"david.plowman@raspberrypi.com"},"content":"Hi Tomi\n\nThanks for that. I had no idea you could write that... the joys of C++!\n\nWould folks like me to send another update?\n\nDavid\n\nOn Fri, 20 Oct 2023 at 08:51, Tomi Valkeinen\n<tomi.valkeinen@ideasonboard.com> wrote:\n>\n> On 12/10/2023 11:29, Kieran Bingham via libcamera-devel wrote:\n> > Hi David,\n> >\n> > Quoting David Plowman via libcamera-devel (2023-10-11 15:02:38)\n> >> We provide access to the various fields of the new SensorConfiguration\n> >> class. The class also needs a constructor so that Python applications\n> >> can make one and put it into the CameraConfiguration.\n> >>\n> >> Signed-off-by: David Plowman <david.plowman@raspberrypi.com>\n> >> ---\n> >>   src/py/libcamera/py_main.cpp | 36 ++++++++++++++++++++++++++++++++++++\n> >>   1 file changed, 36 insertions(+)\n> >>\n> >> diff --git a/src/py/libcamera/py_main.cpp b/src/py/libcamera/py_main.cpp\n> >> index 01fb15a9..d2ce3722 100644\n> >> --- a/src/py/libcamera/py_main.cpp\n> >> +++ b/src/py/libcamera/py_main.cpp\n> >> @@ -112,6 +112,7 @@ PYBIND11_MODULE(_libcamera, m)\n> >>\n> >>          auto pyCameraManager = py::class_<PyCameraManager, std::shared_ptr<PyCameraManager>>(m, \"CameraManager\");\n> >>          auto pyCamera = py::class_<Camera, PyCameraSmartPtr<Camera>>(m, \"Camera\");\n> >> +       auto pySensorConfiguration = py::class_<SensorConfiguration>(m, \"SensorConfiguration\");\n> >>          auto pyCameraConfiguration = py::class_<CameraConfiguration>(m, \"CameraConfiguration\");\n> >>          auto pyCameraConfigurationStatus = py::enum_<CameraConfiguration::Status>(pyCameraConfiguration, \"Status\");\n> >>          auto pyStreamConfiguration = py::class_<StreamConfiguration>(m, \"StreamConfiguration\");\n> >> @@ -281,6 +282,40 @@ PYBIND11_MODULE(_libcamera, m)\n> >>                          return ret;\n> >>                  });\n> >>\n> >> +       pySensorConfiguration\n> >> +               .def(py::init<>())\n> >> +               .def_readwrite(\"bit_depth\", &SensorConfiguration::bitDepth)\n> >> +               .def_readwrite(\"analog_crop\", &SensorConfiguration::analogCrop)\n> >> +               .def_property(\n> >> +                       \"binning\",\n> >> +                       [](SensorConfiguration &self) {\n> >> +                               return py::make_tuple(self.binning.binX, self.binning.binY);\n> >> +                       },\n> >> +                       [](SensorConfiguration &self, py::object value) {\n> >> +                               auto vec = value.cast<std::vector<unsigned int>>();\n> >> +                               if (vec.size() != 2)\n> >> +                                       throw std::runtime_error(\"binning requires iterable of 2 values\");\n> >> +                               self.binning.binX = vec[0];\n> >> +                               self.binning.binY = vec[1];\n> >\n> > This seems reasonable to me. Partially filling in either of binning or\n> > skipping would be invalid.\n> >\n> > Thanks for filling in the rest of the logic:\n> >\n> > Reviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com>\n> >\n> > Tomi - Are you happy with this?\n>\n> I think it's simpler and better to do:\n>\n> .def_property(\n>         \"binning\",\n>         [](SensorConfiguration &self) {\n>                 return std::make_tuple(self.binning.binX, self.binning.binY);\n>         },\n>         [](SensorConfiguration &self, std::tuple<uint32_t, uint32_t> value) {\n>                 self.binning.binX = std::get<0>(value);\n>                 self.binning.binY = std::get<1>(value);\n>         })\n>\n>   Tomi\n>\n>\n> >\n> >\n> >\n> >> +                       })\n> >> +               .def_property(\n> >> +                       \"skipping\",\n> >> +                       [](SensorConfiguration &self) {\n> >> +                               return py::make_tuple(self.skipping.xOddInc, self.skipping.xEvenInc,\n> >> +                                                     self.skipping.yOddInc, self.skipping.yEvenInc);\n> >> +                       },\n> >> +                       [](SensorConfiguration &self, py::object value) {\n> >> +                               auto vec = value.cast<std::vector<unsigned int>>();\n> >> +                               if (vec.size() != 4)\n> >> +                                       throw std::runtime_error(\"skipping requires iterable of 4 values\");\n> >> +                               self.skipping.xOddInc = vec[0];\n> >> +                               self.skipping.xEvenInc = vec[1];\n> >> +                               self.skipping.yOddInc = vec[2];\n> >> +                               self.skipping.yEvenInc = vec[3];\n> >> +                       })\n> >> +               .def_readwrite(\"output_size\", &SensorConfiguration::outputSize)\n> >> +               .def(\"is_valid\", &SensorConfiguration::isValid);\n> >> +\n> >>          pyCameraConfiguration\n> >>                  .def(\"__iter__\", [](CameraConfiguration &self) {\n> >>                          return py::make_iterator<py::return_value_policy::reference_internal>(self);\n> >> @@ -293,6 +328,7 @@ PYBIND11_MODULE(_libcamera, m)\n> >>                       py::return_value_policy::reference_internal)\n> >>                  .def_property_readonly(\"size\", &CameraConfiguration::size)\n> >>                  .def_property_readonly(\"empty\", &CameraConfiguration::empty)\n> >> +               .def_readwrite(\"sensor_config\", &CameraConfiguration::sensorConfig)\n> >>                  .def_readwrite(\"transform\", &CameraConfiguration::transform);\n> >>\n> >>          pyCameraConfigurationStatus\n> >> --\n> >> 2.39.2\n> >>\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 9E306BDCBD\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri, 20 Oct 2023 08:17:23 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id C6D916297F;\n\tFri, 20 Oct 2023 10:17:22 +0200 (CEST)","from mail-qv1-xf33.google.com (mail-qv1-xf33.google.com\n\t[IPv6:2607:f8b0:4864:20::f33])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id B5A8B61DCF\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 20 Oct 2023 10:17:20 +0200 (CEST)","by mail-qv1-xf33.google.com with SMTP id\n\t6a1803df08f44-66d17fd450aso14245216d6.1\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 20 Oct 2023 01:17:20 -0700 (PDT)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1697789842;\n\tbh=piRquVbSLbX2JQCEfEL1bJ1N91Brjc4S+2FRUiYFGFk=;\n\th=References:In-Reply-To:Date:To:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:Cc:\n\tFrom;\n\tb=d/VSYWFS3hSd8r3/dnm9G1kNgUOz1XrLcy9SaGVzFOMO/XGuEEvpaXV6q00vaE5hx\n\tzJGX+t8dzf/sAqSgtSVBv9WTfNx4R5ZSZjMU6F6WiP7xx33ip3U/cJXrNNCCZbX4iL\n\tgWmZ+qrFTFsJ8VTaxdaAYKd5KAMNE9iTIe2uiTdIHyIQIqpdm1oQqKH1YC+t0+/A73\n\toxqrAllP2NHrUDn+rrXgKmGob7h4GgG2AqHmsLJCj92j1sDW2VLCVlAIRIYkDq+Jui\n\tziUXGbtKzxs/9o36RzNYtB+JlheSQF150UXb1hFFTXVCDcz6jpI+Xp7gHCRuilv/B6\n\ta7DXwhZXhzMbw==","v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=raspberrypi.com; s=google; t=1697789839; x=1698394639;\n\tdarn=lists.libcamera.org; \n\th=cc:to:subject:message-id:date:from:in-reply-to:references\n\t:mime-version:from:to:cc:subject:date:message-id:reply-to;\n\tbh=4a9qdbGvHYDmXReBZNrRTzEl71Er5K2MqmD/shCJjMM=;\n\tb=YM8jVIDcNa3msE2Gp9JFC3Z4o73UI4Y8uomfE91l8BrTUT1IQkKjKyRrtHmmWpD+TO\n\tRaCf14HSoYLAh6mwX0iVXrOW/peAsngO+8oHewsEwU0m3AUByLuhBTj1rNgF0N/ms4E4\n\tMOdsYBcnENx08IzaBO4N7hlTs0sQpZHuncFHekuRuV1nsJujX4nbs96azON+FBKGNxXC\n\t4vH52Aaq2HlRtFfZAzSPSdg6YkpAhaNRKC7RHCA0DriaRG+rU1HWAp2mJbWtBmyHwOkX\n\tr5ikZKOXAjAdLIjZ9G40FT70ot4exwYpKVCURr4bK4pTXa1lqtNtt8FLsgwtpYe0+/Ml\n\tno6w=="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (2048-bit key; \n\tunprotected) header.d=raspberrypi.com\n\theader.i=@raspberrypi.com\n\theader.b=\"YM8jVIDc\"; dkim-atps=neutral","X-Google-DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=1e100.net; s=20230601; t=1697789839; x=1698394639;\n\th=cc:to:subject:message-id:date:from:in-reply-to:references\n\t:mime-version:x-gm-message-state:from:to:cc:subject:date:message-id\n\t:reply-to;\n\tbh=4a9qdbGvHYDmXReBZNrRTzEl71Er5K2MqmD/shCJjMM=;\n\tb=xEh8G1zvFG0Ct+tCde8EmD7uXkqjTvoHNJb5CUe1c6S4BMNIzpvtzcdEmeh2LOJM5E\n\tY7k7EhPXtFhWrr+yMsI4NBejk2W+oR9a6o/ZNR9cuagExnfw6aI+s9SVMpRM6S+NxTOM\n\tW5jOPqk7hGCMCuoOfvRZMd7NSHb4Fs6QdXHpG7dhAuFaR6h679PezcXFwLI8cwxoJGDr\n\tMwPuoLXmb/4jYG4BSuBwXsF9y5r4YOVitKPcRc3EQ6lXzXsJ94AJL6uyZQWX0Ca0kWIp\n\t7tsYbdcP8Et9ebHQ3ys34E3Ur4F2VWhnxE5F3BxwxVg8Xiwtueeq/ukpaFCoiD/nECk/\n\tQuTA==","X-Gm-Message-State":"AOJu0Yx4iyXYYohd3ty/b/uRbPhnDGEaLTj5qSZZSzE7TOF5YdI6FeSn\n\tXd/liLNHWnY4JdlaogTuKULNvW7f2UbLdarejBR8iWEFwNjkerNF","X-Google-Smtp-Source":"AGHT+IEMUfpMQJF3Afj7Ax+SauN4XWB+iAXfamJWb+2sqzZxznQTaCwu8Xs6kPX42XyM1kfRtswkbOUEQfksLlMSXD4=","X-Received":"by 2002:a0c:f84d:0:b0:66d:870:771e with SMTP id\n\tg13-20020a0cf84d000000b0066d0870771emr6285104qvo.13.1697789839588;\n\tFri, 20 Oct 2023 01:17:19 -0700 (PDT)","MIME-Version":"1.0","References":"<20231011140238.39058-1-david.plowman@raspberrypi.com>\n\t<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>\n\t<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>","In-Reply-To":"<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>","Date":"Fri, 20 Oct 2023 09:17:08 +0100","Message-ID":"<CAHW6GYL5gzZqRkpCSwYisLWAzY6Wcxb9jAGBAhtoroA4YejZGw@mail.gmail.com>","To":"Tomi Valkeinen <tomi.valkeinen@ideasonboard.com>","Content-Type":"text/plain; charset=\"UTF-8\"","Subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","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>","From":"David Plowman via libcamera-devel <libcamera-devel@lists.libcamera.org>","Reply-To":"David Plowman <david.plowman@raspberrypi.com>","Cc":"libcamera-devel@lists.libcamera.org","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}},{"id":28012,"web_url":"https://patchwork.libcamera.org/comment/28012/","msgid":"<89ef92e0-85e0-4198-a432-6040e4cf59dc@ideasonboard.com>","date":"2023-10-20T08:19:52","subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","submitter":{"id":109,"url":"https://patchwork.libcamera.org/api/people/109/","name":"Tomi Valkeinen","email":"tomi.valkeinen@ideasonboard.com"},"content":"On 20/10/2023 11:17, David Plowman wrote:\n> Hi Tomi\n> \n> Thanks for that. I had no idea you could write that... the joys of C++!\n\nI think usually with pybind11 you should think in terms of C++. Use the \nC++ types whenever possible, as they're more performant and specific \nthan the Python types, and let pybind11 do the conversions between the \nPython and C++ types.\n\n  Tomi\n\n> \n> Would folks like me to send another update?\n> \n> David\n> \n> On Fri, 20 Oct 2023 at 08:51, Tomi Valkeinen\n> <tomi.valkeinen@ideasonboard.com> wrote:\n>>\n>> On 12/10/2023 11:29, Kieran Bingham via libcamera-devel wrote:\n>>> Hi David,\n>>>\n>>> Quoting David Plowman via libcamera-devel (2023-10-11 15:02:38)\n>>>> We provide access to the various fields of the new SensorConfiguration\n>>>> class. The class also needs a constructor so that Python applications\n>>>> can make one and put it into the CameraConfiguration.\n>>>>\n>>>> Signed-off-by: David Plowman <david.plowman@raspberrypi.com>\n>>>> ---\n>>>>    src/py/libcamera/py_main.cpp | 36 ++++++++++++++++++++++++++++++++++++\n>>>>    1 file changed, 36 insertions(+)\n>>>>\n>>>> diff --git a/src/py/libcamera/py_main.cpp b/src/py/libcamera/py_main.cpp\n>>>> index 01fb15a9..d2ce3722 100644\n>>>> --- a/src/py/libcamera/py_main.cpp\n>>>> +++ b/src/py/libcamera/py_main.cpp\n>>>> @@ -112,6 +112,7 @@ PYBIND11_MODULE(_libcamera, m)\n>>>>\n>>>>           auto pyCameraManager = py::class_<PyCameraManager, std::shared_ptr<PyCameraManager>>(m, \"CameraManager\");\n>>>>           auto pyCamera = py::class_<Camera, PyCameraSmartPtr<Camera>>(m, \"Camera\");\n>>>> +       auto pySensorConfiguration = py::class_<SensorConfiguration>(m, \"SensorConfiguration\");\n>>>>           auto pyCameraConfiguration = py::class_<CameraConfiguration>(m, \"CameraConfiguration\");\n>>>>           auto pyCameraConfigurationStatus = py::enum_<CameraConfiguration::Status>(pyCameraConfiguration, \"Status\");\n>>>>           auto pyStreamConfiguration = py::class_<StreamConfiguration>(m, \"StreamConfiguration\");\n>>>> @@ -281,6 +282,40 @@ PYBIND11_MODULE(_libcamera, m)\n>>>>                           return ret;\n>>>>                   });\n>>>>\n>>>> +       pySensorConfiguration\n>>>> +               .def(py::init<>())\n>>>> +               .def_readwrite(\"bit_depth\", &SensorConfiguration::bitDepth)\n>>>> +               .def_readwrite(\"analog_crop\", &SensorConfiguration::analogCrop)\n>>>> +               .def_property(\n>>>> +                       \"binning\",\n>>>> +                       [](SensorConfiguration &self) {\n>>>> +                               return py::make_tuple(self.binning.binX, self.binning.binY);\n>>>> +                       },\n>>>> +                       [](SensorConfiguration &self, py::object value) {\n>>>> +                               auto vec = value.cast<std::vector<unsigned int>>();\n>>>> +                               if (vec.size() != 2)\n>>>> +                                       throw std::runtime_error(\"binning requires iterable of 2 values\");\n>>>> +                               self.binning.binX = vec[0];\n>>>> +                               self.binning.binY = vec[1];\n>>>\n>>> This seems reasonable to me. Partially filling in either of binning or\n>>> skipping would be invalid.\n>>>\n>>> Thanks for filling in the rest of the logic:\n>>>\n>>> Reviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com>\n>>>\n>>> Tomi - Are you happy with this?\n>>\n>> I think it's simpler and better to do:\n>>\n>> .def_property(\n>>          \"binning\",\n>>          [](SensorConfiguration &self) {\n>>                  return std::make_tuple(self.binning.binX, self.binning.binY);\n>>          },\n>>          [](SensorConfiguration &self, std::tuple<uint32_t, uint32_t> value) {\n>>                  self.binning.binX = std::get<0>(value);\n>>                  self.binning.binY = std::get<1>(value);\n>>          })\n>>\n>>    Tomi\n>>\n>>\n>>>\n>>>\n>>>\n>>>> +                       })\n>>>> +               .def_property(\n>>>> +                       \"skipping\",\n>>>> +                       [](SensorConfiguration &self) {\n>>>> +                               return py::make_tuple(self.skipping.xOddInc, self.skipping.xEvenInc,\n>>>> +                                                     self.skipping.yOddInc, self.skipping.yEvenInc);\n>>>> +                       },\n>>>> +                       [](SensorConfiguration &self, py::object value) {\n>>>> +                               auto vec = value.cast<std::vector<unsigned int>>();\n>>>> +                               if (vec.size() != 4)\n>>>> +                                       throw std::runtime_error(\"skipping requires iterable of 4 values\");\n>>>> +                               self.skipping.xOddInc = vec[0];\n>>>> +                               self.skipping.xEvenInc = vec[1];\n>>>> +                               self.skipping.yOddInc = vec[2];\n>>>> +                               self.skipping.yEvenInc = vec[3];\n>>>> +                       })\n>>>> +               .def_readwrite(\"output_size\", &SensorConfiguration::outputSize)\n>>>> +               .def(\"is_valid\", &SensorConfiguration::isValid);\n>>>> +\n>>>>           pyCameraConfiguration\n>>>>                   .def(\"__iter__\", [](CameraConfiguration &self) {\n>>>>                           return py::make_iterator<py::return_value_policy::reference_internal>(self);\n>>>> @@ -293,6 +328,7 @@ PYBIND11_MODULE(_libcamera, m)\n>>>>                        py::return_value_policy::reference_internal)\n>>>>                   .def_property_readonly(\"size\", &CameraConfiguration::size)\n>>>>                   .def_property_readonly(\"empty\", &CameraConfiguration::empty)\n>>>> +               .def_readwrite(\"sensor_config\", &CameraConfiguration::sensorConfig)\n>>>>                   .def_readwrite(\"transform\", &CameraConfiguration::transform);\n>>>>\n>>>>           pyCameraConfigurationStatus\n>>>> --\n>>>> 2.39.2\n>>>>\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 2C13AC3272\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri, 20 Oct 2023 08:19:58 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id A08566297F;\n\tFri, 20 Oct 2023 10:19:57 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[213.167.242.64])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 2852761DCF\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 20 Oct 2023 10:19:56 +0200 (CEST)","from [192.168.88.20] (91-158-145-56.elisa-laajakaista.fi\n\t[91.158.145.56])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id 62A9DB2A;\n\tFri, 20 Oct 2023 10:19:47 +0200 (CEST)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1697789997;\n\tbh=j7h9IPAgCUvHPjWIjTXfmFICD1Q9/yhXeAkxmuI/YYc=;\n\th=Date:To:References:In-Reply-To:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:Cc:\n\tFrom;\n\tb=B8VnouX+dlCbkaCRNlmqdNx9n6Ozq/Lmge1d36NKG8QzhHo7SRJdgTECTPiWZzMz7\n\t5HpfI9tqfm6/bM2WIzuZ5wNC5BDjzaduoWvxcgV+gUCBfLFk5vVn4wMKkkxr3oiG6v\n\t/xURZecLcB8cOYhyXAyz5rHb4gnb6WKBO9FIbSVcqkJBhWTKlSBq5dYvsDRt8H1idf\n\t2fcpUICxn3dfJrHaj+VpTIfItnA+0SLtNrgI5ExyO46uvqxIUGws/ZW7w+Iuipi99j\n\tno5O7lpW5Kh9nvYx4G0N3hAp2Qv01y10vneXgcriZfcaC+joD4ILT627KGqPKjo6bF\n\t7uRdkZmb3Ud9Q==","v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1697789987;\n\tbh=j7h9IPAgCUvHPjWIjTXfmFICD1Q9/yhXeAkxmuI/YYc=;\n\th=Date:Subject:To:Cc:References:From:In-Reply-To:From;\n\tb=M2Q32gPRrGzkenXbrJxOBGbpl2oo+/JR7bY7jRW4kj8xmGjUG0sZl7jrOmMF58TMP\n\tAX4Qe1b/n4T4gtXjJAIYTIsnUdhgOG/BALsUciln7o88y+6myCbWc/lvT4SlMxMV19\n\t+KQwImKa9GQyar/8XdVVGsYQ1c/m8TJZtTzNTFhI="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (1024-bit key; \n\tunprotected) header.d=ideasonboard.com\n\theader.i=@ideasonboard.com\n\theader.b=\"M2Q32gPR\"; dkim-atps=neutral","Message-ID":"<89ef92e0-85e0-4198-a432-6040e4cf59dc@ideasonboard.com>","Date":"Fri, 20 Oct 2023 11:19:52 +0300","MIME-Version":"1.0","User-Agent":"Mozilla Thunderbird","Content-Language":"en-US","To":"David Plowman <david.plowman@raspberrypi.com>","References":"<20231011140238.39058-1-david.plowman@raspberrypi.com>\n\t<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>\n\t<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>\n\t<CAHW6GYL5gzZqRkpCSwYisLWAzY6Wcxb9jAGBAhtoroA4YejZGw@mail.gmail.com>","Autocrypt":"addr=tomi.valkeinen@ideasonboard.com; keydata=\n\t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","In-Reply-To":"<CAHW6GYL5gzZqRkpCSwYisLWAzY6Wcxb9jAGBAhtoroA4YejZGw@mail.gmail.com>","Content-Type":"text/plain; charset=UTF-8; format=flowed","Content-Transfer-Encoding":"7bit","Subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","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>","From":"Tomi Valkeinen via libcamera-devel\n\t<libcamera-devel@lists.libcamera.org>","Reply-To":"Tomi Valkeinen <tomi.valkeinen@ideasonboard.com>","Cc":"libcamera-devel@lists.libcamera.org","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}},{"id":28013,"web_url":"https://patchwork.libcamera.org/comment/28013/","msgid":"<169779003402.3350128.17774841226719883064@ping.linuxembedded.co.uk>","date":"2023-10-20T08:20:34","subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","submitter":{"id":4,"url":"https://patchwork.libcamera.org/api/people/4/","name":"Kieran Bingham","email":"kieran.bingham@ideasonboard.com"},"content":"Quoting Tomi Valkeinen (2023-10-20 08:51:08)\n> On 12/10/2023 11:29, Kieran Bingham via libcamera-devel wrote:\n> > Hi David,\n> > \n> > Quoting David Plowman via libcamera-devel (2023-10-11 15:02:38)\n> >> We provide access to the various fields of the new SensorConfiguration\n> >> class. The class also needs a constructor so that Python applications\n> >> can make one and put it into the CameraConfiguration.\n> >>\n> >> Signed-off-by: David Plowman <david.plowman@raspberrypi.com>\n> >> ---\n> >>   src/py/libcamera/py_main.cpp | 36 ++++++++++++++++++++++++++++++++++++\n> >>   1 file changed, 36 insertions(+)\n> >>\n> >> diff --git a/src/py/libcamera/py_main.cpp b/src/py/libcamera/py_main.cpp\n> >> index 01fb15a9..d2ce3722 100644\n> >> --- a/src/py/libcamera/py_main.cpp\n> >> +++ b/src/py/libcamera/py_main.cpp\n> >> @@ -112,6 +112,7 @@ PYBIND11_MODULE(_libcamera, m)\n> >>   \n> >>          auto pyCameraManager = py::class_<PyCameraManager, std::shared_ptr<PyCameraManager>>(m, \"CameraManager\");\n> >>          auto pyCamera = py::class_<Camera, PyCameraSmartPtr<Camera>>(m, \"Camera\");\n> >> +       auto pySensorConfiguration = py::class_<SensorConfiguration>(m, \"SensorConfiguration\");\n> >>          auto pyCameraConfiguration = py::class_<CameraConfiguration>(m, \"CameraConfiguration\");\n> >>          auto pyCameraConfigurationStatus = py::enum_<CameraConfiguration::Status>(pyCameraConfiguration, \"Status\");\n> >>          auto pyStreamConfiguration = py::class_<StreamConfiguration>(m, \"StreamConfiguration\");\n> >> @@ -281,6 +282,40 @@ PYBIND11_MODULE(_libcamera, m)\n> >>                          return ret;\n> >>                  });\n> >>   \n> >> +       pySensorConfiguration\n> >> +               .def(py::init<>())\n> >> +               .def_readwrite(\"bit_depth\", &SensorConfiguration::bitDepth)\n> >> +               .def_readwrite(\"analog_crop\", &SensorConfiguration::analogCrop)\n> >> +               .def_property(\n> >> +                       \"binning\",\n> >> +                       [](SensorConfiguration &self) {\n> >> +                               return py::make_tuple(self.binning.binX, self.binning.binY);\n> >> +                       },\n> >> +                       [](SensorConfiguration &self, py::object value) {\n> >> +                               auto vec = value.cast<std::vector<unsigned int>>();\n> >> +                               if (vec.size() != 2)\n> >> +                                       throw std::runtime_error(\"binning requires iterable of 2 values\");\n> >> +                               self.binning.binX = vec[0];\n> >> +                               self.binning.binY = vec[1];\n> > \n> > This seems reasonable to me. Partially filling in either of binning or\n> > skipping would be invalid.\n> > \n> > Thanks for filling in the rest of the logic:\n> > \n> > Reviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com>\n> > \n> > Tomi - Are you happy with this?\n> \n> I think it's simpler and better to do:\n> \n> .def_property(\n>         \"binning\",\n>         [](SensorConfiguration &self) {\n>                 return std::make_tuple(self.binning.binX, self.binning.binY);\n>         },\n>         [](SensorConfiguration &self, std::tuple<uint32_t, uint32_t> value) {\n>                 self.binning.binX = std::get<0>(value);\n>                 self.binning.binY = std::get<1>(value);\n\nDoes the std::get<> add the bounds checking that allows the vec.size()\ncheck to be removed?\n\n>         })\n> \n\nI'm afraid I already merged this I think.\n\nIf it's a cleanup/fixup - can  you submit a patch please?\n\n--\nKieran\n\n\n>   Tomi\n> \n> \n> > \n> > \n> > \n> >> +                       })\n> >> +               .def_property(\n> >> +                       \"skipping\",\n> >> +                       [](SensorConfiguration &self) {\n> >> +                               return py::make_tuple(self.skipping.xOddInc, self.skipping.xEvenInc,\n> >> +                                                     self.skipping.yOddInc, self.skipping.yEvenInc);\n> >> +                       },\n> >> +                       [](SensorConfiguration &self, py::object value) {\n> >> +                               auto vec = value.cast<std::vector<unsigned int>>();\n> >> +                               if (vec.size() != 4)\n> >> +                                       throw std::runtime_error(\"skipping requires iterable of 4 values\");\n> >> +                               self.skipping.xOddInc = vec[0];\n> >> +                               self.skipping.xEvenInc = vec[1];\n> >> +                               self.skipping.yOddInc = vec[2];\n> >> +                               self.skipping.yEvenInc = vec[3];\n> >> +                       })\n> >> +               .def_readwrite(\"output_size\", &SensorConfiguration::outputSize)\n> >> +               .def(\"is_valid\", &SensorConfiguration::isValid);\n> >> +\n> >>          pyCameraConfiguration\n> >>                  .def(\"__iter__\", [](CameraConfiguration &self) {\n> >>                          return py::make_iterator<py::return_value_policy::reference_internal>(self);\n> >> @@ -293,6 +328,7 @@ PYBIND11_MODULE(_libcamera, m)\n> >>                       py::return_value_policy::reference_internal)\n> >>                  .def_property_readonly(\"size\", &CameraConfiguration::size)\n> >>                  .def_property_readonly(\"empty\", &CameraConfiguration::empty)\n> >> +               .def_readwrite(\"sensor_config\", &CameraConfiguration::sensorConfig)\n> >>                  .def_readwrite(\"transform\", &CameraConfiguration::transform);\n> >>   \n> >>          pyCameraConfigurationStatus\n> >> -- \n> >> 2.39.2\n> >>\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 61CA9C3272\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri, 20 Oct 2023 08:20:38 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id 1E47462980;\n\tFri, 20 Oct 2023 10:20:38 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 6E84262973\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 20 Oct 2023 10:20:36 +0200 (CEST)","from pendragon.ideasonboard.com\n\t(aztw-30-b2-v4wan-166917-cust845.vm26.cable.virginm.net\n\t[82.37.23.78])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id F06BDC80;\n\tFri, 20 Oct 2023 10:20:27 +0200 (CEST)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1697790038;\n\tbh=H+JM6Tkv7qOSQZeVnb/+66pKJEdI6xtRToaB4AttHIs=;\n\th=In-Reply-To:References:To:Date:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:\n\tFrom;\n\tb=QhrmPMZxRC6iIJT3dxAhshxs2BK9peP9Miyf4C0w2oJHp2s7a6dOyCMrO0RPD6W0n\n\tJS2yz77m4+GRwuEIl/JtpQQn0t+aEAGzlhXpfUB3cwH3PfWk85mPwwLp8qXA35shAJ\n\tvvRuTtdpAhuJz4eOKtzNkRboSgZw+kghXHT17PWVxhtkVSKaT0D8QfYneRix60aq/K\n\tSmkXu0eN5eWNpjsuz8rSNI7ov6ZrQvQqdS5pRThEMBvEAFBIzSMeC4eeOu0Sv/8yRd\n\tRuWNLeccKfBbUL1BacoBNBgkEByVWeOtG5FmO/O+oNcmGZKTdUTE/XPFz08HI2USjO\n\t9Xi6ljPmsWUYw==","v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1697790028;\n\tbh=H+JM6Tkv7qOSQZeVnb/+66pKJEdI6xtRToaB4AttHIs=;\n\th=In-Reply-To:References:Subject:From:To:Date:From;\n\tb=LpKdAPpzR6bTnocJPs6OSysBM0oLFNiyRcAFvsTqgapg6x5byF8IO88Ww14Xst0D3\n\tsotd1jHJOwX3OQR9w+KRhSUV5FXD/poam59TFMGypus8juHXvM9D2mgBuNQg/JA4aa\n\tdb4GpnRxjk4coHwNrUh7N2XFc8+r1GylGJkNWhr4="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (1024-bit key; \n\tunprotected) header.d=ideasonboard.com\n\theader.i=@ideasonboard.com\n\theader.b=\"LpKdAPpz\"; dkim-atps=neutral","Content-Type":"text/plain; charset=\"utf-8\"","MIME-Version":"1.0","Content-Transfer-Encoding":"quoted-printable","In-Reply-To":"<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>","References":"<20231011140238.39058-1-david.plowman@raspberrypi.com>\n\t<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>\n\t<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>","To":"David Plowman <david.plowman@raspberrypi.com>,\n\tTomi Valkeinen <tomi.valkeinen@ideasonboard.com>,\n\tlibcamera-devel@lists.libcamera.org","Date":"Fri, 20 Oct 2023 09:20:34 +0100","Message-ID":"<169779003402.3350128.17774841226719883064@ping.linuxembedded.co.uk>","User-Agent":"alot/0.10","Subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","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>","From":"Kieran Bingham via libcamera-devel\n\t<libcamera-devel@lists.libcamera.org>","Reply-To":"Kieran Bingham <kieran.bingham@ideasonboard.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}},{"id":28014,"web_url":"https://patchwork.libcamera.org/comment/28014/","msgid":"<77617f12-3ff1-4a17-b26b-ea424b75cc74@ideasonboard.com>","date":"2023-10-20T08:21:39","subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","submitter":{"id":109,"url":"https://patchwork.libcamera.org/api/people/109/","name":"Tomi Valkeinen","email":"tomi.valkeinen@ideasonboard.com"},"content":"On 20/10/2023 11:20, Kieran Bingham wrote:\n> Quoting Tomi Valkeinen (2023-10-20 08:51:08)\n>> On 12/10/2023 11:29, Kieran Bingham via libcamera-devel wrote:\n>>> Hi David,\n>>>\n>>> Quoting David Plowman via libcamera-devel (2023-10-11 15:02:38)\n>>>> We provide access to the various fields of the new SensorConfiguration\n>>>> class. The class also needs a constructor so that Python applications\n>>>> can make one and put it into the CameraConfiguration.\n>>>>\n>>>> Signed-off-by: David Plowman <david.plowman@raspberrypi.com>\n>>>> ---\n>>>>    src/py/libcamera/py_main.cpp | 36 ++++++++++++++++++++++++++++++++++++\n>>>>    1 file changed, 36 insertions(+)\n>>>>\n>>>> diff --git a/src/py/libcamera/py_main.cpp b/src/py/libcamera/py_main.cpp\n>>>> index 01fb15a9..d2ce3722 100644\n>>>> --- a/src/py/libcamera/py_main.cpp\n>>>> +++ b/src/py/libcamera/py_main.cpp\n>>>> @@ -112,6 +112,7 @@ PYBIND11_MODULE(_libcamera, m)\n>>>>    \n>>>>           auto pyCameraManager = py::class_<PyCameraManager, std::shared_ptr<PyCameraManager>>(m, \"CameraManager\");\n>>>>           auto pyCamera = py::class_<Camera, PyCameraSmartPtr<Camera>>(m, \"Camera\");\n>>>> +       auto pySensorConfiguration = py::class_<SensorConfiguration>(m, \"SensorConfiguration\");\n>>>>           auto pyCameraConfiguration = py::class_<CameraConfiguration>(m, \"CameraConfiguration\");\n>>>>           auto pyCameraConfigurationStatus = py::enum_<CameraConfiguration::Status>(pyCameraConfiguration, \"Status\");\n>>>>           auto pyStreamConfiguration = py::class_<StreamConfiguration>(m, \"StreamConfiguration\");\n>>>> @@ -281,6 +282,40 @@ PYBIND11_MODULE(_libcamera, m)\n>>>>                           return ret;\n>>>>                   });\n>>>>    \n>>>> +       pySensorConfiguration\n>>>> +               .def(py::init<>())\n>>>> +               .def_readwrite(\"bit_depth\", &SensorConfiguration::bitDepth)\n>>>> +               .def_readwrite(\"analog_crop\", &SensorConfiguration::analogCrop)\n>>>> +               .def_property(\n>>>> +                       \"binning\",\n>>>> +                       [](SensorConfiguration &self) {\n>>>> +                               return py::make_tuple(self.binning.binX, self.binning.binY);\n>>>> +                       },\n>>>> +                       [](SensorConfiguration &self, py::object value) {\n>>>> +                               auto vec = value.cast<std::vector<unsigned int>>();\n>>>> +                               if (vec.size() != 2)\n>>>> +                                       throw std::runtime_error(\"binning requires iterable of 2 values\");\n>>>> +                               self.binning.binX = vec[0];\n>>>> +                               self.binning.binY = vec[1];\n>>>\n>>> This seems reasonable to me. Partially filling in either of binning or\n>>> skipping would be invalid.\n>>>\n>>> Thanks for filling in the rest of the logic:\n>>>\n>>> Reviewed-by: Kieran Bingham <kieran.bingham@ideasonboard.com>\n>>>\n>>> Tomi - Are you happy with this?\n>>\n>> I think it's simpler and better to do:\n>>\n>> .def_property(\n>>          \"binning\",\n>>          [](SensorConfiguration &self) {\n>>                  return std::make_tuple(self.binning.binX, self.binning.binY);\n>>          },\n>>          [](SensorConfiguration &self, std::tuple<uint32_t, uint32_t> value) {\n>>                  self.binning.binX = std::get<0>(value);\n>>                  self.binning.binY = std::get<1>(value);\n> \n> Does the std::get<> add the bounds checking that allows the vec.size()\n> check to be removed?\n\nIt's the \"std::tuple<uint32_t, uint32_t> value\" that forces the types \nand the size.\n\n  Tomi\n\n> \n>>          })\n>>\n> \n> I'm afraid I already merged this I think.\n> \n> If it's a cleanup/fixup - can  you submit a patch please?\n> \n> --\n> Kieran\n> \n> \n>>    Tomi\n>>\n>>\n>>>\n>>>\n>>>\n>>>> +                       })\n>>>> +               .def_property(\n>>>> +                       \"skipping\",\n>>>> +                       [](SensorConfiguration &self) {\n>>>> +                               return py::make_tuple(self.skipping.xOddInc, self.skipping.xEvenInc,\n>>>> +                                                     self.skipping.yOddInc, self.skipping.yEvenInc);\n>>>> +                       },\n>>>> +                       [](SensorConfiguration &self, py::object value) {\n>>>> +                               auto vec = value.cast<std::vector<unsigned int>>();\n>>>> +                               if (vec.size() != 4)\n>>>> +                                       throw std::runtime_error(\"skipping requires iterable of 4 values\");\n>>>> +                               self.skipping.xOddInc = vec[0];\n>>>> +                               self.skipping.xEvenInc = vec[1];\n>>>> +                               self.skipping.yOddInc = vec[2];\n>>>> +                               self.skipping.yEvenInc = vec[3];\n>>>> +                       })\n>>>> +               .def_readwrite(\"output_size\", &SensorConfiguration::outputSize)\n>>>> +               .def(\"is_valid\", &SensorConfiguration::isValid);\n>>>> +\n>>>>           pyCameraConfiguration\n>>>>                   .def(\"__iter__\", [](CameraConfiguration &self) {\n>>>>                           return py::make_iterator<py::return_value_policy::reference_internal>(self);\n>>>> @@ -293,6 +328,7 @@ PYBIND11_MODULE(_libcamera, m)\n>>>>                        py::return_value_policy::reference_internal)\n>>>>                   .def_property_readonly(\"size\", &CameraConfiguration::size)\n>>>>                   .def_property_readonly(\"empty\", &CameraConfiguration::empty)\n>>>> +               .def_readwrite(\"sensor_config\", &CameraConfiguration::sensorConfig)\n>>>>                   .def_readwrite(\"transform\", &CameraConfiguration::transform);\n>>>>    \n>>>>           pyCameraConfigurationStatus\n>>>> -- \n>>>> 2.39.2\n>>>>\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 184A0C3272\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri, 20 Oct 2023 08:21:41 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id C65BA62980;\n\tFri, 20 Oct 2023 10:21:40 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id BFE2C62973\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 20 Oct 2023 10:21:39 +0200 (CEST)","from [192.168.88.20] (91-158-145-56.elisa-laajakaista.fi\n\t[91.158.145.56])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id 3BC7DB2A;\n\tFri, 20 Oct 2023 10:21:31 +0200 (CEST)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1697790100;\n\tbh=hBlENtw08Pn1HPsXjC5eC+cGbce1RIyOf/3L30nrXis=;\n\th=Date:To:References:In-Reply-To:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:\n\tFrom;\n\tb=iO21tgxPt6Q/hmIYV8CGD3g6MLpZOOY7UO3X9FIe6sFa9+Px/qj7AG81wOjxrx8EN\n\tk4rJ+dWnuSoyGHYVrWRtfSeIha2ATmtRoVYcvSShBji7EryoZKoONqZD3se5Rd1s4Q\n\tCUQgrHpOmKeQ3GmQqiND3RaRb3Y9Qin1MBkubMCs6gtm41Bev/3g1i0UgI6eAGEmdq\n\trRtL1JyiIT7cTwkOJyYsRiin1608vq/6Ea64VmWzWhP+Axkraq1SE9Pcil3XqSXtDw\n\to18/J5PA3xAqM/H84p+Dj0U3SELpn2qun2nRRxfxNw1m6c324NyhoWulvxKx4P4mhp\n\t9QU5RknEv2lAw==","v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1697790091;\n\tbh=hBlENtw08Pn1HPsXjC5eC+cGbce1RIyOf/3L30nrXis=;\n\th=Date:Subject:To:References:From:In-Reply-To:From;\n\tb=qLCS1qam4XFtDq6yOq+OYGEV5BgVZVTP0fwjRpfm3kQDby8LpLt8m72dtrId3hXJO\n\tsS18qo2rlcVGqQf1RTCP0xFi+HMqR31OGHbRWQzoxkwhiVuWP1NRI+Niq7sEUfdvxf\n\tMTo2AdPsLEX/y9d4t99xYFuDx0mNqYK0E+fp/alA="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (1024-bit key; \n\tunprotected) header.d=ideasonboard.com\n\theader.i=@ideasonboard.com\n\theader.b=\"qLCS1qam\"; dkim-atps=neutral","Message-ID":"<77617f12-3ff1-4a17-b26b-ea424b75cc74@ideasonboard.com>","Date":"Fri, 20 Oct 2023 11:21:39 +0300","MIME-Version":"1.0","User-Agent":"Mozilla Thunderbird","Content-Language":"en-US","To":"Kieran Bingham <kieran.bingham@ideasonboard.com>,\n\tDavid Plowman <david.plowman@raspberrypi.com>,\n\tlibcamera-devel@lists.libcamera.org","References":"<20231011140238.39058-1-david.plowman@raspberrypi.com>\n\t<169709938795.277971.18084373113331775642@ping.linuxembedded.co.uk>\n\t<2548a5e0-503f-45c8-9dcc-00ed3d4f227f@ideasonboard.com>\n\t<169779003402.3350128.17774841226719883064@ping.linuxembedded.co.uk>","Autocrypt":"addr=tomi.valkeinen@ideasonboard.com; keydata=\n\t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","In-Reply-To":"<169779003402.3350128.17774841226719883064@ping.linuxembedded.co.uk>","Content-Type":"text/plain; charset=UTF-8; format=flowed","Content-Transfer-Encoding":"7bit","Subject":"Re: [libcamera-devel] [PATCH v2] py: Add the SensorConfiguration\n\tclass","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>","From":"Tomi Valkeinen via libcamera-devel\n\t<libcamera-devel@lists.libcamera.org>","Reply-To":"Tomi Valkeinen <tomi.valkeinen@ideasonboard.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}}]