From patchwork Tue May 17 14:33:13 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15925 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id C2E01C326C for ; Tue, 17 May 2022 14:33:54 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 3121965662; Tue, 17 May 2022 16:33:54 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798034; bh=nuViv9JC7+6/Yx1PMRRtFJVY+pz5y00/lrjlJxDVKPI=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=ryiAVgAkQw3CJQugo0u05xkfq6fwoCsqXoPSE0fDPJM235z08X4D05Msc37K4ZN+I u/j6iRILOCUMl9tT79GMq3n3AwqigKKSQ8mHHUIhGKBkUH4/4y7Y5np+ZfIhtxxzYF 9QZxZJCoAanpsMCvQywI0BLG+KJzslvIz/EccL5MQpLFSOg7YW2p+e9EIXVngR58Py h2vCBmYmZZYkP93GA6BB8BlMNX92qlF626sy3osELOOJ5rbNzxYPGlUjynqraOY2/I QBnOfNwG53yi7VWeeVRUy4+Gk/boStgZK6+PyfvhJ23o+vw5MJo/mVu1BjjpO59zQD C5+CXfTOdFhhA== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id EC6036041D for ; Tue, 17 May 2022 16:33:51 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="LMgXURdl"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 607046DC; Tue, 17 May 2022 16:33:51 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798031; bh=nuViv9JC7+6/Yx1PMRRtFJVY+pz5y00/lrjlJxDVKPI=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=LMgXURdlhr4TQbRr4TTeCASzohQglnPiaFB5ofKFNjvH8M6zPtIl+AQxPGjJwCBWO u1oOUWVamOc0lABntJxwX3M+qJVylGsajMxIdda4zmoXY4bdm3JqT1TdsL+XbYSV84 78FHY89YOkcvuy7HEiLUPRcS9CV207VV2y3X+/k0= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:13 +0300 Message-Id: <20220517143325.71784-2-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 01/13] py: meson: fix comment about stubs X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" At least pyright seems to be able to use the stubs from the libcamera-stubs directory, so no need to copy the generated files. Adjust the comment accordingly. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/libcamera/meson.build | 1 - 1 file changed, 1 deletion(-) diff --git a/src/py/libcamera/meson.build b/src/py/libcamera/meson.build index 0cd7c75b..38f619d0 100644 --- a/src/py/libcamera/meson.build +++ b/src/py/libcamera/meson.build @@ -63,4 +63,3 @@ install_data(['__init__.py'], install_dir : destdir) # \todo Generate stubs when building. See https://peps.python.org/pep-0484/#stub-files # Note: Depends on pybind11-stubgen. To generate pylibcamera stubs: # $ PYTHONPATH=build/src/py pybind11-stubgen --no-setup-py -o build/src/py libcamera -# $ mv build/src/py/libcamera-stubs/* build/src/py/libcamera/ From patchwork Tue May 17 14:33:14 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15926 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id C0999C3256 for ; Tue, 17 May 2022 14:33:55 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 83EE86041E; Tue, 17 May 2022 16:33:55 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798035; bh=OFNUJIPjBd8sjbcQV4mr3FTMsE4thcfDX+7+k+bf3BU=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=kZywUa3tSBr2U4npmphvyJOyYAkzYdfmcu/hqqyNBYAfCF1X6Ttd9H9Yk/myIw4NX v0NhkZazHtlH39H6DsqmTE9BZQvBMaBOyL6UbK8PbjkBfjU/e9Qu8lVOxZlM2ghL6L yxUzCMAS5dCQDmXS7dWG3uibFUiJ53U+sY+fRq7GR3IORPPdgCqvCzxWNDPyO62Lfg U7fY+g1AFt5iM9s1GR9bVxkPFnNSCAJ4nfLa90+BkNVpNDXPfg3LnnehOYDZx2Z7Lt CyEx56Z31xC+xap6i+XjOOuiVfn8ZctP4TjuBXlFlFpQfm7iQNQM2EOhtH5zkyeDE6 XyLLoUug8vNiw== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 744736041E for ; Tue, 17 May 2022 16:33:52 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="HAw3lSbR"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id DC7968D3; Tue, 17 May 2022 16:33:51 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798032; bh=OFNUJIPjBd8sjbcQV4mr3FTMsE4thcfDX+7+k+bf3BU=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=HAw3lSbRv46v1Ato8MzIoThtQj8QcKWImmsdOOSWYcMIDEhy1W1yzZ+PLZmIyt4D3 e+cJC0TIZA+gAEn+sFGFgQn0rGLdpIJURtreGuD1M9SqpJbHZLTW5DTsibdE2fe7iT 7OBPy6DP81pLPgw5xq8IXRTOSlEGsPKV7GRoTDCE= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:14 +0300 Message-Id: <20220517143325.71784-3-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 02/13] py: meson: add pystubs build target X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Add a 'pystubs' build target for building the python stubs. For now this needs to be ran manually. I didn't figure out how to generate the stubs after the libcamera bindings are built. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/libcamera/meson.build | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/src/py/libcamera/meson.build b/src/py/libcamera/meson.build index 38f619d0..32e74504 100644 --- a/src/py/libcamera/meson.build +++ b/src/py/libcamera/meson.build @@ -60,6 +60,18 @@ run_command('ln', '-fsT', '../../../../src/py/libcamera/__init__.py', install_data(['__init__.py'], install_dir : destdir) -# \todo Generate stubs when building. See https://peps.python.org/pep-0484/#stub-files +# \todo Generate stubs when building, and install them. +# See https://peps.python.org/pep-0484/#stub-files # Note: Depends on pybind11-stubgen. To generate pylibcamera stubs: # $ PYTHONPATH=build/src/py pybind11-stubgen --no-setup-py -o build/src/py libcamera +# The target below can be ran manually, but how to create a meson target that +# is run if pycamera is built? + +stubgen = find_program('pybind11-stubgen', required : false) + +if stubgen.found() + run_target('pystubs', + depends: pycamera, + env: {'PYTHONPATH': meson.project_build_root() / 'src' / 'py'}, + command: [stubgen, '--no-setup-py', '-o', meson.project_build_root() / 'src' / 'py', 'libcamera']) +endif From patchwork Tue May 17 14:33:15 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15927 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 5A6D3C326C for ; Tue, 17 May 2022 14:33:56 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id E224E65668; Tue, 17 May 2022 16:33:55 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798036; bh=08UHnwYK2QMPLHUbZuBUvvtvloDpqUVnDTZ3FO99ziM=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=SWo3n2DguddPzV7+Lmku98dsubqqyN5UJbGQ9jYrkTu3mqvvBub5h89z3iwvKtAy8 IVXJqyS2AwbeKUDognIw17TrMRkMNXozODmN9Z03o5shjtduu/p0FHEleMHVuBR7Qz qDgVNq9bUBV3vLZRAhl955UQmn6jbPlVSZfnYeQu+M8vqnIaaFsEp+OBk8ciMHyRYY zZeMBtLg3/1B2XxjM5bUGJRFSDQEBRjK7oU/tAnQXgVQ5ZuKWXkZu5uiFm8XrKUqmi zWEvxCJ9HIN7K9trQ8R/mhc7CvxQj/CYJcHax3gllErhg32XjggpCaJBwiTQz0XzDk TGaFusnGmYldQ== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id EF68D6565F for ; Tue, 17 May 2022 16:33:52 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="A7bkfzyv"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 6620B8E6; Tue, 17 May 2022 16:33:52 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798032; bh=08UHnwYK2QMPLHUbZuBUvvtvloDpqUVnDTZ3FO99ziM=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=A7bkfzyvzYK8YMK+0yocUPfKkv1zyoZ6rdZ5JY7zdYZCbUAYZ669azD6SE4zuquxf jm/3RuFd9ytF2A8oxhh1RH7FJA8/e7XsopcXwYeXYa1n8GktzpdeDFA5WlUe8ShSqC pZ9qfIFm8fR4mVKZynbdv6dLTueqApd0tFpdH9WQ= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:15 +0300 Message-Id: <20220517143325.71784-4-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 03/13] py: pymain: fix indent X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Fix two minor mis-indents. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/libcamera/pymain.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/py/libcamera/pymain.cpp b/src/py/libcamera/pymain.cpp index fb89975c..af22205e 100644 --- a/src/py/libcamera/pymain.cpp +++ b/src/py/libcamera/pymain.cpp @@ -394,7 +394,7 @@ PYBIND11_MODULE(_libcamera, m) pyStreamConfiguration .def("__str__", &StreamConfiguration::toString) .def_property_readonly("stream", &StreamConfiguration::stream, - py::return_value_policy::reference_internal) + py::return_value_policy::reference_internal) .def_property( "size", [](StreamConfiguration &self) { @@ -416,7 +416,7 @@ PYBIND11_MODULE(_libcamera, m) .def_readwrite("frame_size", &StreamConfiguration::frameSize) .def_readwrite("buffer_count", &StreamConfiguration::bufferCount) .def_property_readonly("formats", &StreamConfiguration::formats, - py::return_value_policy::reference_internal) + py::return_value_policy::reference_internal) .def_readwrite("color_space", &StreamConfiguration::colorSpace); pyStreamFormats From patchwork Tue May 17 14:33:16 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15928 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 2A723C3256 for ; Tue, 17 May 2022 14:33:58 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id D500365666; Tue, 17 May 2022 16:33:57 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798037; bh=YTNuPtMuA18Tsx5/GaoNG9fs4gImrS8u3Jjoehg356M=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=tAu86gNoHb9IehrSf1Ktc0FrHezA38qVy2kGpaYOyDHDC0Qv8CWIOnx3aWuvSyJP+ ljM+rqq5bUKNfr7elE0h1eoLvQD+7N9jk2dinaKfjWITdcCdRRWW01WXzlokouI8S/ ZiUkkoAaO+ObmJ5qXYgPTOpWgFoU9HGgfLpO1F6kkgxStU3av0mC5XLRQRbffsFcCm p6ApXGigHmAi5ClpeKkWbAGGxxXLl4trHFONL9n07/ohH56Yq7py+VO6afZc1ncBi3 H4P8rM6cysTWGaMZnZAExwXXnRi/aZnyDYOMQq/xIq7QuQUxM2N2yKhMNs4+ZKw0Pp 5uUoC6M3GewkQ== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id B07A06041E for ; Tue, 17 May 2022 16:33:53 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="SXsV+pL6"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 0ECDFD41; Tue, 17 May 2022 16:33:52 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798033; bh=YTNuPtMuA18Tsx5/GaoNG9fs4gImrS8u3Jjoehg356M=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=SXsV+pL6I0tGF/F6Ay+4Kt2RVZ9X0wrOzM8GqRl5GJLqUrF2bPxcbLggeVwxRBaie So+YsewEgyY6BIKCA6J/0cZzHy5+si9XlnYTSb4sxlvgDxUE/9i90OMiHn1BpUsSwa PS9bb3kuPavXnHD0qlS/KlKzvN/xYmIpULareOIM= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:16 +0300 Message-Id: <20220517143325.71784-5-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 04/13] py: unittests: fix selector fd use X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" pyright complains about passing fileobj to os.read. Indeed, the parameter should be an int, but I guess fileobj gets automatically converted. In any case, using the fd is better. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- test/py/unittests.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/py/unittests.py b/test/py/unittests.py index cbc00ff3..9326358d 100755 --- a/test/py/unittests.py +++ b/test/py/unittests.py @@ -262,8 +262,8 @@ class SimpleCaptureMethods(CameraTesterBase): running = True while running: events = sel.select() - for key, mask in events: - os.read(key.fileobj, 8) + for key, _ in events: + os.read(key.fd, 8) ready_reqs = cm.get_ready_requests() From patchwork Tue May 17 14:33:17 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15929 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id A394EC326D for ; Tue, 17 May 2022 14:33:58 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 3D18C6041D; Tue, 17 May 2022 16:33:58 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798038; bh=uUO9E4zBomuA+wF8p3Q+nMamxEdaL4uqXD+Aia+1+Mw=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=Zz3mvGIxFPrzT0mQwAJEe9Ar9Aer3WEKITWVci4uBdK7rJjB53DnQpt46y7YPsBpQ /lG08itAnkHLFPHExkEjaUCe6P7ARmHyb2QI2jmDe7+5+nh7xqSWG7r3cCQL9kCbDM 4dqCVq58J5pTABiAcC43obKx3cDSImDqDN1X68m9JIL6MX8Sva0m9vIqQuVNOQ8dwy BLvBzNULY1Gq+YhT3EJPL4aErOc+SsYeN+Y0/lOfD+eBzezZT6QqziuoViOgVwVg9z MJG6jHO/oELh3xIo5si/xSAzzJal2npCwzwosYS90GuHegvI3mHIM32GUu4KH+jChN IPey+qWMmYTUQ== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [213.167.242.64]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 2C4F465661 for ; Tue, 17 May 2022 16:33:54 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="ooco2jjY"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 91917D59; Tue, 17 May 2022 16:33:53 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798033; bh=uUO9E4zBomuA+wF8p3Q+nMamxEdaL4uqXD+Aia+1+Mw=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=ooco2jjY/glQ/MAESRrSirbOKHWXjS5m0lypxVcKC7sA7wF4ir8V7pL2skPYM7dL1 XzUBmVviSgURXHwNt8uIeNaASkHIdyoLwNRa08ae9r4A6z16qIw8QjdLJuWxB6asXJ HZlNpqSdgWjbWygjCSj2yIp1YOFdGx0V8YyHh32A= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:17 +0300 Message-Id: <20220517143325.71784-6-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 05/13] py: unittests: verify that cam and cm are freed X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Add checks to CameraTesterBase to verify that both the Camera and the CameraManager gets freed. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- test/py/unittests.py | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/test/py/unittests.py b/test/py/unittests.py index 9326358d..4c214f0a 100755 --- a/test/py/unittests.py +++ b/test/py/unittests.py @@ -83,6 +83,9 @@ class CameraTesterBase(BaseTestCase): self.cm = None raise Exception('Failed to acquire camera') + self.wr_cam = weakref.ref(self.cam) + self.wr_cm = weakref.ref(self.cm) + def tearDown(self): # If a test fails, the camera may be in running state. So always stop. self.cam.stop() @@ -94,6 +97,9 @@ class CameraTesterBase(BaseTestCase): self.cam = None self.cm = None + self.assertIsNone(self.wr_cm()) + self.assertIsNone(self.wr_cam()) + class AllocatorTestMethods(CameraTesterBase): def test_allocator(self): From patchwork Tue May 17 14:33:18 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15930 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 85F13C326E for ; Tue, 17 May 2022 14:33:59 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 90BB56150E; Tue, 17 May 2022 16:33:58 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798038; bh=CtW1NDm3DIh/r1HdoChtqD1UBdwwy7iA9E7BTzTyYPc=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=mOcxJ+z1pOelE0D8XdcFogY0gLn/k7IhTe3SF1PQ08vCKVDC4Bgt+Xj3fK6u3r4RK r14mQkz0MJYQniWLKUuh2zerM4CK2kx7+VEVTkZnBnUcmMDUv+DjqitKujgI+dtp4q 7Dsa/nhSBi3KKJHUxGlhpuJ+aPH5d0pXSROQhdrR1AC4zBW6tJqTT6nL+Yi3tLeiPq ZG5uixoi6lUa2Sd1/E+t/+ZI7lHdFOJpReMfVWZtVjU/iQ4ug5U9K8JJO07m9xVczf qcsUYT2VFUn+YnCclivxueqljfy6Q0NDo1T4Rum+Ks5LSjhOXUu8XMWMzcKymXdDj6 UJWHGbqlk0/jw== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [213.167.242.64]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id A4CB065665 for ; Tue, 17 May 2022 16:33:54 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="YWja2Eoe"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 1B80DDA8; Tue, 17 May 2022 16:33:54 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798034; bh=CtW1NDm3DIh/r1HdoChtqD1UBdwwy7iA9E7BTzTyYPc=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=YWja2EoeCoBcw/puNHr9uBSPP9CAaBSV+JwwZXViNUXSaKZfkriTvUK4VdH3Jpsj3 VhPoXEkSYNBlk8fHC5zlKL/GFWlGhASK93NfB3J0rUE8di94ULLzmrappHRxesrx+a FvBEpp4DRFMocg9d/tfr1RZwQaoiQt8RkQvFgnmM= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:18 +0300 Message-Id: <20220517143325.71784-7-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 06/13] py: unittests: make typechecker happy X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Add some annotations and self.assertIsNotNone() calls to remove the typechecker warnings. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- test/py/unittests.py | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/test/py/unittests.py b/test/py/unittests.py index 4c214f0a..2ea5ca35 100755 --- a/test/py/unittests.py +++ b/test/py/unittests.py @@ -10,6 +10,7 @@ import libcamera as libcam import os import selectors import time +import typing import unittest import weakref @@ -70,6 +71,9 @@ class SimpleTestMethods(BaseTestCase): class CameraTesterBase(BaseTestCase): + cm: typing.Any + cam: typing.Any + def setUp(self): self.cm = libcam.CameraManager.singleton() self.cam = next((cam for cam in self.cm.cameras if 'platform/vimc' in cam.id), None) @@ -131,6 +135,7 @@ class AllocatorTestMethods(CameraTesterBase): wr_allocator = weakref.ref(allocator) buffers = allocator.buffers(stream) + self.assertIsNotNone(buffers) buffers = None buffer = allocator.buffers(stream)[0] @@ -166,6 +171,8 @@ class SimpleCaptureMethods(CameraTesterBase): streamconfig = camconfig.at(0) fmts = streamconfig.formats + self.assertIsNotNone(fmts) + fmts = None ret = cam.configure(camconfig) self.assertZero(ret) @@ -225,6 +232,7 @@ class SimpleCaptureMethods(CameraTesterBase): streamconfig = camconfig.at(0) fmts = streamconfig.formats + self.assertIsNotNone(fmts) ret = cam.configure(camconfig) self.assertZero(ret) @@ -348,9 +356,9 @@ if __name__ == '__main__': gc.unfreeze() gc.collect() - obs_after = get_all_objects([obs_before]) + obs_after = get_all_objects([obs_before]) # type: ignore - before = create_type_count_map(obs_before) + before = create_type_count_map(obs_before) # type: ignore after = create_type_count_map(obs_after) leaks = diff_type_count_maps(before, after) From patchwork Tue May 17 14:33:19 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15931 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id D8C94C326F for ; Tue, 17 May 2022 14:33:59 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 0D1B865670; Tue, 17 May 2022 16:33:59 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798039; bh=NI44KOnwRz0zUZLq5P8HPPG0KXibhhJuHsRNwPXF7l8=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=wCKOOmsXCv/VmR/KK7unh9hwjwBJEPFMQnZqxB7QJRGZdgSZEgnzAn3Nlw4veJoZq LN/uC6qTTo/Umy683yHJmVi/NOcPjELKYnLupiY5hY9nZsjCD6o+9FfEcHsKj1fNZu F+xohl7IujTXaKUUYO4mi7BoP7lAgXUbU3+zJAfl/0quca5Uf9oN7W0m+QJ3Bejauw 36UKDFWrz3QUTm38DEFFkTdGEaqNlOrj81h4+01zzQGctZZvKYtWfQHps2uAPqcDa2 CvNlM+NJVwATfzSaC5rl8Egs1p+gXwUebp5ZDtqmT6eJHmd0RfwF6hF2NWEdnyDhvY /KihUWtmZCbDA== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 300C76565E for ; Tue, 17 May 2022 16:33:55 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="mxTHjsw6"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 9A6BA4A8; Tue, 17 May 2022 16:33:54 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798035; bh=NI44KOnwRz0zUZLq5P8HPPG0KXibhhJuHsRNwPXF7l8=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=mxTHjsw6eAniiQjETS864vMFP7iz6o+ncV3PAJaEgTQ6IENbgoJjEimmwMkibA+Jv L2REMtdoDChefJdrZFk/dtjABusKzi9MRshmXuED0ZILeMdJedKmhKsP8oKyZFD63j 4H4Yy2Pgazp0/9VlCxOTLTPfKHWcKsK1cbwh0xKQ= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:19 +0300 Message-Id: <20220517143325.71784-8-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 07/13] py: cam.py: exit on exception X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Catch exceptions in the event_handler, as they would get ignored otherwise. Print the exception and return False so that the main loop exits. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/cam/cam.py | 23 ++++++++++++++--------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/src/py/cam/cam.py b/src/py/cam/cam.py index 012b191c..c7da97d7 100755 --- a/src/py/cam/cam.py +++ b/src/py/cam/cam.py @@ -11,6 +11,7 @@ import binascii import libcamera as libcam import os import sys +import traceback class CustomAction(argparse.Action): @@ -286,19 +287,23 @@ def capture_start(contexts): # Called from renderer when there is a libcamera event def event_handler(state): - cm = state['cm'] - contexts = state['contexts'] + try: + cm = state['cm'] + contexts = state['contexts'] - os.read(cm.efd, 8) + os.read(cm.efd, 8) - reqs = cm.get_ready_requests() + reqs = cm.get_ready_requests() - for req in reqs: - ctx = next(ctx for ctx in contexts if ctx['idx'] == req.cookie) - request_handler(state, ctx, req) + for req in reqs: + ctx = next(ctx for ctx in contexts if ctx['idx'] == req.cookie) + request_handler(state, ctx, req) - running = any(ctx['reqs-completed'] < ctx['opt-capture'] for ctx in contexts) - return running + running = any(ctx['reqs-completed'] < ctx['opt-capture'] for ctx in contexts) + return running + except Exception as e: + traceback.print_exc() + return False def request_handler(state, ctx, req): From patchwork Tue May 17 14:33:20 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15932 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 19C11C3270 for ; Tue, 17 May 2022 14:34:00 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 6D6B965683; Tue, 17 May 2022 16:33:59 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798039; bh=hFwAE5tnu4o6+UhDKvevxclNwmDGxiwsg/j5d7ZJsUo=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=2ooL/cPTWSCZWB+bi0lWpFeBmPULlEXi70rH8gYbzrym7yW1Lf3h9gURWKnWbX75Z uwgb64apGj2XxrRGkVhgvvnQN6u9l4qK6N2a5IivgGM5AIUztKdZg7UM6dZywxhKLN xHBSKv7XvJtip2cV8S7WBjRtnSN98mmOc2zitJg0axo/OMNmzuSoDuqcAL2jZI+8vI dtbupZ6CLrcOdl7hgsO+xElDPohQxoCYjkQTnjN8N1uWAOACp0ONABeMCIZ32563I/ JW+VkbyEDksh3r38utMzXdGr6uVKlMrgA4j5cXaukdKnKvAs0dofCDY76tzKjZJbd9 fN1z3KDDraTkQ== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id A78866566B for ; Tue, 17 May 2022 16:33:55 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="DNEfYBRs"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 22D678E6; Tue, 17 May 2022 16:33:55 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798035; bh=hFwAE5tnu4o6+UhDKvevxclNwmDGxiwsg/j5d7ZJsUo=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=DNEfYBRscUID0CkpUu3wPCLShTmUwuBuUwifYKJGMyUs/gb1JQ4mB7c8Gritz8/q9 etzzVZraJfSnOkZOGKjMK/s4gPXYE0aJqaOj+wlcdtFz3QUrxOQj8Zjns42eEbvhAE kAHFXVPGfJjasJ9Uw+QEh6t8Pp2R/9DOSFTVHDow= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:20 +0300 Message-Id: <20220517143325.71784-9-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 08/13] py: cam_kms: support multiplanar formats X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Support multiplanar formats in the kms renderer. Tested with RPi and NV12. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/cam/cam_kms.py | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/py/cam/cam_kms.py b/src/py/cam/cam_kms.py index ae6be277..f1844717 100644 --- a/src/py/cam/cam_kms.py +++ b/src/py/cam/cam_kms.py @@ -10,6 +10,7 @@ FMT_MAP = { 'YUYV': pykms.PixelFormat.YUYV, 'ARGB8888': pykms.PixelFormat.ARGB8888, 'XRGB8888': pykms.PixelFormat.XRGB8888, + 'NV12': pykms.PixelFormat.NV12, } @@ -133,10 +134,16 @@ class KMSRenderer: for fb in ctx['allocator'].buffers(stream): w, h = cfg.size - stride = cfg.stride - fd = fb.fd(0) + fds = [] + strides = [] + offsets = [] + for i in range(fb.num_planes): + fds.append(fb.fd(i)) + strides.append(cfg.stride) + offsets.append(fb.offset(i)) + drmfb = pykms.DmabufFramebuffer(self.card, w, h, fmt, - [fd], [stride], [0]) + fds, strides, offsets) self.cam_2_drm[fb] = drmfb idx += 1 From patchwork Tue May 17 14:33:21 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15933 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id D9810C3271 for ; Tue, 17 May 2022 14:34:00 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 6D4C065667; Tue, 17 May 2022 16:34:00 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798040; bh=U0Vdm2wpBtY0+BD7NSs1FupKjGp9MeIUUX1p4o37m6M=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=1xWnfODdSw3JIMu5RSUBwLNjeinvnHfRNdA0t/lXLn+ELFWpkNKMKlXPpeUNSIEie umgDa6t7bOBpgV86usR3l+2GK2ZsbJlVtTRkNlrR/YHWFWTfNaUDtScYhbsTVxuQvt ehlpQLwTkMaXiBG3EtaBEiWyFqEnAEYYYe4cMzzA046OUgMRinv62AJaNMq1D0g79z L49Z1Sue5gtXWV9zJQc9NHLbbXY+Tz/xpHWhZ4+gmk5uO1eSjG0eJ3wNjyCnW0m12y 4smYjStJTGrrL5EWDDgJqaJvP0lrndmhLK2zRjdWCxVL8akc3xw5luA9pnWxCvexFA T9yhM2k9o4M1w== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 336246566D for ; Tue, 17 May 2022 16:33:56 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="MUsbNzKa"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 9EF4CD59; Tue, 17 May 2022 16:33:55 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798036; bh=U0Vdm2wpBtY0+BD7NSs1FupKjGp9MeIUUX1p4o37m6M=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=MUsbNzKaEWYIkqCSShrIW+6vhAZc4Kk5qElwtToVfYtwOandLNSlGNmKWAWXNMIg3 kfne+i0rcKTaKdfk2c6GkZ/Gyz5PC0q4PfDSFCOnwezU2ulXEoJWKjmnJM59kuuQ0Q S7S3PJStYhoonxBChXXWqWvbPyiFQHBL1OkkTv08= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:21 +0300 Message-Id: <20220517143325.71784-10-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 09/13] py: cam_kms: fix multistream display X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Instead of doing an atomic commit for each stream, do a single commit for the two planes. This fixes the issue that only the first plane was actually shown. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/cam/cam_kms.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/py/cam/cam_kms.py b/src/py/cam/cam_kms.py index f1844717..d8ff0284 100644 --- a/src/py/cam/cam_kms.py +++ b/src/py/cam/cam_kms.py @@ -75,12 +75,13 @@ class KMSRenderer: buffers = drmreq['camreq'].buffers + req = pykms.AtomicReq(self.card) + for stream, fb in buffers.items(): drmfb = self.cam_2_drm.get(fb, None) - - req = pykms.AtomicReq(self.card) self.add_plane(req, stream, drmfb) - req.commit() + + req.commit() def handle_page_flip(self, frame, time): old = self.current From patchwork Tue May 17 14:33:22 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15934 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 662F1C3272 for ; Tue, 17 May 2022 14:34:01 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 0F49865672; Tue, 17 May 2022 16:34:01 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798041; bh=8GuO9DI9fiK5P9BAiXMxXcpWXmNvj/HwwBP8uS4gTBQ=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=XmygCfhzA7GMiLLiVB5tcjNKmO3at35B9wuIBTP7RGgKP67IKixcYaWWtMRbPNVug QOkjEwRgi3YSCKYO92E8HO9knl5JgERFFGP+RHL4/5VRX8qMSXuDHbcxB4ixGSxEEk qep90n7FMlLeZWqxgAWjtmDQnX7j6Lqh2es7Br6GhwhqcRwF8bp0JwW41p2WJsQ6AV NocMpzQS98MPbfZieZliUNfYbVee+QG6t+9M0eBtoJGNnNodlfev1bPktkOTTDIqt9 1TB8U8pvDYa/N9QRhr63fcydKI6p8m63Bp6E33+OFCZJxW+ETa8qSSHMGphuHuwDx9 pnESWYwZVVmiQ== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [213.167.242.64]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id AABB765665 for ; Tue, 17 May 2022 16:33:56 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="tz55ja+8"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 2641FEEE; Tue, 17 May 2022 16:33:56 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798036; bh=8GuO9DI9fiK5P9BAiXMxXcpWXmNvj/HwwBP8uS4gTBQ=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=tz55ja+8LJseVKXP8TpZSo8zShcJu2AOiuG/U/Ai+ACBr4PUbcZtSH6CqzBsePDDO bZe3KyvkX+xExu9qOnhEBgwp1h8/AFvxT59a7YYAsLccY/UfKC2REU5AlkanzMkXzd c0rjk2fI+nJClE13mk4eaFnU9TJq3Aav9j9EEcwY= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:22 +0300 Message-Id: <20220517143325.71784-11-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 10/13] py: cam_qt: cosmetic cleanups X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Drop irrelevant or wrong comments, merge separate_components() into demosaic(), and add mfb_to_rgb(). No functional changes. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/cam/cam_qt.py | 64 +++++++++----------------------------------- 1 file changed, 13 insertions(+), 51 deletions(-) diff --git a/src/py/cam/cam_qt.py b/src/py/cam/cam_qt.py index 5753f0b2..fb485b9b 100644 --- a/src/py/cam/cam_qt.py +++ b/src/py/cam/cam_qt.py @@ -19,19 +19,8 @@ def rgb_to_pix(rgb): return pix -def separate_components(data, r0, g0, g1, b0): - # Now to split the data up into its red, green, and blue components. The - # Bayer pattern of the OV5647 sensor is BGGR. In other words the first - # row contains alternating green/blue elements, the second row contains - # alternating red/green elements, and so on as illustrated below: - # - # GBGBGBGBGBGBGB - # RGRGRGRGRGRGRG - # GBGBGBGBGBGBGB - # RGRGRGRGRGRGRG - # - # Please note that if you use vflip or hflip to change the orientation - # of the capture, you must flip the Bayer pattern accordingly +def demosaic(data, r0, g0, g1, b0): + # Separate the components from the Bayer data to RGB planes rgb = np.zeros(data.shape + (3,), dtype=data.dtype) rgb[r0[1]::2, r0[0]::2, 0] = data[r0[1]::2, r0[0]::2] # Red @@ -39,17 +28,9 @@ def separate_components(data, r0, g0, g1, b0): rgb[g1[1]::2, g1[0]::2, 1] = data[g1[1]::2, g1[0]::2] # Green rgb[b0[1]::2, b0[0]::2, 2] = data[b0[1]::2, b0[0]::2] # Blue - return rgb - - -def demosaic(rgb, r0, g0, g1, b0): - # At this point we now have the raw Bayer data with the correct values - # and colors but the data still requires de-mosaicing and - # post-processing. If you wish to do this yourself, end the script here! - # # Below we present a fairly naive de-mosaic method that simply # calculates the weighted average of a pixel based on the pixels - # surrounding it. The weighting is provided b0[1] a b0[1]te representation of + # surrounding it. The weighting is provided by a byte representation of # the Bayer filter which we construct first: bayer = np.zeros(rgb.shape, dtype=np.uint8) @@ -69,29 +50,6 @@ def demosaic(rgb, r0, g0, g1, b0): borders = (window[0] - 1, window[1] - 1) border = (borders[0] // 2, borders[1] // 2) - # rgb_pad = np.zeros(( - # rgb.shape[0] + borders[0], - # rgb.shape[1] + borders[1], - # rgb.shape[2]), dtype=rgb.dtype) - # rgb_pad[ - # border[0]:rgb_pad.shape[0] - border[0], - # border[1]:rgb_pad.shape[1] - border[1], - # :] = rgb - # rgb = rgb_pad - # - # bayer_pad = np.zeros(( - # bayer.shape[0] + borders[0], - # bayer.shape[1] + borders[1], - # bayer.shape[2]), dtype=bayer.dtype) - # bayer_pad[ - # border[0]:bayer_pad.shape[0] - border[0], - # border[1]:bayer_pad.shape[1] - border[1], - # :] = bayer - # bayer = bayer_pad - - # In numpy >=1.7.0 just use np.pad (version in Raspbian is 1.6.2 at the - # time of writing...) - # rgb = np.pad(rgb, [ (border[0], border[0]), (border[1], border[1]), @@ -168,7 +126,7 @@ def to_rgb(fmt, size, data): bayer_pattern = fmt[1:5] bitspp = int(fmt[5:]) - # TODO: shifting leaves the lowest bits 0 + # \todo shifting leaves the lowest bits 0 if bitspp == 8: data = data.reshape((h, w)) data = data.astype(np.uint16) << 8 @@ -195,8 +153,7 @@ def to_rgb(fmt, size, data): assert(idx != -1) b0 = (idx % 2, idx // 2) - rgb = separate_components(data, r0, g0, g1, b0) - rgb = demosaic(rgb, r0, g0, g1, b0) + rgb = demosaic(data, r0, g0, g1, b0) rgb = (rgb >> 8).astype(np.uint8) else: @@ -205,6 +162,13 @@ def to_rgb(fmt, size, data): return rgb +# A naive format conversion to 24-bit RGB +def mfb_to_rgb(mfb, cfg): + data = np.array(mfb.planes[0], dtype=np.uint8) + rgb = to_rgb(cfg.pixel_format, cfg.size, data) + return rgb + + class QtRenderer: def __init__(self, state): self.state = state @@ -334,9 +298,7 @@ class MainWindow(QtWidgets.QWidget): qim = ImageQt(img).copy() pix = QtGui.QPixmap.fromImage(qim) else: - data = np.array(mfb.planes[0], dtype=np.uint8) - rgb = to_rgb(cfg.pixel_format, cfg.size, data) - + rgb = mfb_to_rgb(mfb, cfg) if rgb is None: raise Exception('Format not supported: ' + cfg.pixel_format) From patchwork Tue May 17 14:33:23 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15935 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 1C983C326C for ; Tue, 17 May 2022 14:34:02 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id BC36265673; Tue, 17 May 2022 16:34:01 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798041; bh=9r65xbs9FAdQNxxQWnFIS9Zkox9Wiza5TrnqK5rgZ3k=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=ai3gm0TbkNBmvCbZIq8CM8YFGn1MvJ8T+Dz1wrhisC09BdiXnL0HjlCcbkK2VSHod 2a/gsHA7O4xNJWMrkwEyiSddLorvPEENwMDvGiDL6S3ipnnawEQo4DZ95jmXN82EWF 5r3nT7uKLBEAfyb5ucdQAcCMRdT/rLYIum97sBGG8/Qvz244dD37zadiMVSuNyklrV VRoLaTFYtvc6fk90GsOFMkSH7JTwoRDUbTDGCAurCNV6kHOSvqed2n7fZ02pzd69+r Qjw4cqjQPDs9S+qjvIkHfI09J3bgqZGw1NTvfZCvG9fu4BqnSlbpTUKo8bUTSbp7hX u+/6XCX6OPKng== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 4423D6150E for ; Tue, 17 May 2022 16:33:57 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="OV50FHy6"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id A7956FA2; Tue, 17 May 2022 16:33:56 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798037; bh=9r65xbs9FAdQNxxQWnFIS9Zkox9Wiza5TrnqK5rgZ3k=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=OV50FHy6y5wSxv3az3r3wuItV0kBWOvqSXcH0lKKaMbuX01qIn/YreGHQ6frsSc6z 5u8n5q+NPKHxRpGRNUBtL6MXnR90oJLDIwk3rF30aI8lFMQ7EdEveZyaQ6ebYdAV8y Yvqt7gG28H79cmNqJWhXkMLkU1NevZx9GgPr0mAg= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:23 +0300 Message-Id: <20220517143325.71784-12-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 11/13] py: implement PixelFormat class X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Implement PixelFormat bindings properly with a PixelFormat class. Change the bindings to use the new class instead of a string. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/cam/cam.py | 2 +- src/py/cam/cam_kms.py | 10 +-------- src/py/cam/cam_qt.py | 4 +++- src/py/cam/cam_qtgl.py | 17 +-------------- src/py/cam/gl_helpers.py | 8 ------- src/py/libcamera/pymain.cpp | 42 ++++++++++++++++++------------------- 6 files changed, 27 insertions(+), 56 deletions(-) diff --git a/src/py/cam/cam.py b/src/py/cam/cam.py index c7da97d7..001fb9de 100755 --- a/src/py/cam/cam.py +++ b/src/py/cam/cam.py @@ -164,7 +164,7 @@ def configure(ctx): stream_config.size = (stream_opts['width'], stream_opts['height']) if 'pixelformat' in stream_opts: - stream_config.pixel_format = stream_opts['pixelformat'] + stream_config.pixel_format = libcam.PixelFormat(stream_opts['pixelformat']) stat = camconfig.validate() diff --git a/src/py/cam/cam_kms.py b/src/py/cam/cam_kms.py index d8ff0284..04381da1 100644 --- a/src/py/cam/cam_kms.py +++ b/src/py/cam/cam_kms.py @@ -5,14 +5,6 @@ import pykms import selectors import sys -FMT_MAP = { - 'RGB888': pykms.PixelFormat.RGB888, - 'YUYV': pykms.PixelFormat.YUYV, - 'ARGB8888': pykms.PixelFormat.ARGB8888, - 'XRGB8888': pykms.PixelFormat.XRGB8888, - 'NV12': pykms.PixelFormat.NV12, -} - class KMSRenderer: def __init__(self, state): @@ -120,7 +112,7 @@ class KMSRenderer: cfg = stream.configuration fmt = cfg.pixel_format - fmt = FMT_MAP[fmt] + fmt = pykms.PixelFormat(fmt.fourcc) plane = self.resman.reserve_generic_plane(self.crtc, fmt) assert(plane is not None) diff --git a/src/py/cam/cam_qt.py b/src/py/cam/cam_qt.py index fb485b9b..45a30aeb 100644 --- a/src/py/cam/cam_qt.py +++ b/src/py/cam/cam_qt.py @@ -87,6 +87,8 @@ def to_rgb(fmt, size, data): w = size[0] h = size[1] + fmt = str(fmt) + if fmt == 'YUYV': # YUV422 yuyv = data.reshape((h, w // 2 * 4)) @@ -293,7 +295,7 @@ class MainWindow(QtWidgets.QWidget): w, h = cfg.size pitch = cfg.stride - if cfg.pixel_format == 'MJPEG': + if str(cfg.pixel_format) == 'MJPEG': img = Image.open(BytesIO(mfb.planes[0])) qim = ImageQt(img).copy() pix = QtGui.QPixmap.fromImage(qim) diff --git a/src/py/cam/cam_qtgl.py b/src/py/cam/cam_qtgl.py index 8a95994e..261accb8 100644 --- a/src/py/cam/cam_qtgl.py +++ b/src/py/cam/cam_qtgl.py @@ -30,14 +30,6 @@ from OpenGL.GL import shaders from gl_helpers import * -# libcamera format string -> DRM fourcc -FMT_MAP = { - 'RGB888': 'RG24', - 'XRGB8888': 'XR24', - 'ARGB8888': 'AR24', - 'YUYV': 'YUYV', -} - class EglState: def __init__(self): @@ -204,12 +196,6 @@ class MainWindow(QtWidgets.QWidget): self.current[ctx['idx']] = [] for stream in ctx['streams']: - fmt = stream.configuration.pixel_format - size = stream.configuration.size - - if fmt not in FMT_MAP: - raise Exception('Unsupported pixel format: ' + str(fmt)) - self.textures[stream] = None num_tiles = len(self.textures) @@ -281,8 +267,7 @@ class MainWindow(QtWidgets.QWidget): def create_texture(self, stream, fb): cfg = stream.configuration - fmt = cfg.pixel_format - fmt = str_to_fourcc(FMT_MAP[fmt]) + fmt = cfg.pixel_format.fourcc w, h = cfg.size attribs = [ diff --git a/src/py/cam/gl_helpers.py b/src/py/cam/gl_helpers.py index ac5e6889..53b3e9df 100644 --- a/src/py/cam/gl_helpers.py +++ b/src/py/cam/gl_helpers.py @@ -30,14 +30,6 @@ def getglEGLImageTargetTexture2DOES(): glEGLImageTargetTexture2DOES = getglEGLImageTargetTexture2DOES() -# \todo This can be dropped when we have proper PixelFormat bindings -def str_to_fourcc(str): - assert(len(str) == 4) - fourcc = 0 - for i, v in enumerate([ord(c) for c in str]): - fourcc |= v << (i * 8) - return fourcc - def get_gl_extensions(): n = GLint() diff --git a/src/py/libcamera/pymain.cpp b/src/py/libcamera/pymain.cpp index af22205e..97b05903 100644 --- a/src/py/libcamera/pymain.cpp +++ b/src/py/libcamera/pymain.cpp @@ -8,7 +8,6 @@ /* * \todo Add geometry classes (Point, Rectangle...) * \todo Add bindings for the ControlInfo class - * \todo Add bindings for the PixelFormat class */ #include @@ -173,6 +172,7 @@ PYBIND11_MODULE(_libcamera, m) auto pyColorSpaceTransferFunction = py::enum_(pyColorSpace, "TransferFunction"); auto pyColorSpaceYcbcrEncoding = py::enum_(pyColorSpace, "YcbcrEncoding"); auto pyColorSpaceRange = py::enum_(pyColorSpace, "Range"); + auto pyPixelFormat = py::class_(m, "PixelFormat"); /* Global functions */ m.def("log_set_level", &logSetLevel); @@ -404,14 +404,7 @@ PYBIND11_MODULE(_libcamera, m) self.size.width = std::get<0>(size); self.size.height = std::get<1>(size); }) - .def_property( - "pixel_format", - [](StreamConfiguration &self) { - return self.pixelFormat.toString(); - }, - [](StreamConfiguration &self, std::string fmt) { - self.pixelFormat = PixelFormat::fromString(fmt); - }) + .def_readwrite("pixel_format", &StreamConfiguration::pixelFormat) .def_readwrite("stride", &StreamConfiguration::stride) .def_readwrite("frame_size", &StreamConfiguration::frameSize) .def_readwrite("buffer_count", &StreamConfiguration::bufferCount) @@ -420,22 +413,15 @@ PYBIND11_MODULE(_libcamera, m) .def_readwrite("color_space", &StreamConfiguration::colorSpace); pyStreamFormats - .def_property_readonly("pixel_formats", [](StreamFormats &self) { - std::vector fmts; - for (auto &fmt : self.pixelformats()) - fmts.push_back(fmt.toString()); - return fmts; - }) - .def("sizes", [](StreamFormats &self, const std::string &pixelFormat) { - auto fmt = PixelFormat::fromString(pixelFormat); + .def_property_readonly("pixel_formats", &StreamFormats::pixelformats) + .def("sizes", [](StreamFormats &self, const PixelFormat &pixelFormat) { std::vector> fmts; - for (const auto &s : self.sizes(fmt)) + for (const auto &s : self.sizes(pixelFormat)) fmts.push_back(std::make_tuple(s.width, s.height)); return fmts; }) - .def("range", [](StreamFormats &self, const std::string &pixelFormat) { - auto fmt = PixelFormat::fromString(pixelFormat); - const auto &range = self.range(fmt); + .def("range", [](StreamFormats &self, const PixelFormat &pixelFormat) { + const auto &range = self.range(pixelFormat); return make_tuple(std::make_tuple(range.hStep, range.vStep), std::make_tuple(range.min.width, range.min.height), std::make_tuple(range.max.width, range.max.height)); @@ -648,4 +634,18 @@ PYBIND11_MODULE(_libcamera, m) pyColorSpaceRange .value("Full", ColorSpace::Range::Full) .value("Limited", ColorSpace::Range::Limited); + + pyPixelFormat + .def(py::init<>()) + .def(py::init()) + .def(py::init<>([](const std::string &str) { + return PixelFormat::fromString(str); + })) + .def_property_readonly("fourcc", &PixelFormat::fourcc) + .def_property_readonly("modifier", &PixelFormat::modifier) + .def(py::self == py::self) + .def("__str__", &PixelFormat::toString) + .def("__repr__", [](const PixelFormat &self) { + return "libcamera.PixelFormat('" + self.toString() + "')"; + }); } From patchwork Tue May 17 14:33:24 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15936 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id AB43CC3256 for ; Tue, 17 May 2022 14:34:04 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 25D5B65663; Tue, 17 May 2022 16:34:04 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798044; bh=lJxPhYu1Q9PAKcijXta3z7JGTZfAb86TDDJn4rPYuAQ=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=P2DaFzIKuhEUndxG6t97BD+wT/dw4zV8HigttWcqK7xMpwjAGUeNR6FHxt5hmRJgW rWKS1X7IlCwrPS7OhDECh8VIZFnekmu4dENAUAJXQPyFMVfz3C4QteLH3gLT4y8yuL GsSvDqHKF88RE3CfnAXXiuqtKApngDh3ocYBijhmW7PjoiBVwQkWUsoB9klYrGn9S9 dEZKjqlNgu1g1xRYprECqSo8qH417dsE7oDMacDVR8bH79aoCOxNBkpP6/34U64QXM QVttsuOO/a3rJ7AnNIa71zMoEJLfs4IfTDNHP+nveNp1479K5M/MlByr2h+GiQbJzF crjU9jzNrNfTQ== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id D314265676 for ; Tue, 17 May 2022 16:33:57 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="YD0Wxpyp"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id 3E1B74A8; Tue, 17 May 2022 16:33:57 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798037; bh=lJxPhYu1Q9PAKcijXta3z7JGTZfAb86TDDJn4rPYuAQ=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=YD0WxpypdNVjfaWqdwkRE6lVbNCWD+r2AP0GDXf9Jhm1QTHWdMy7/UtMeV8y8DCBx bEuGn3IKuEB+PdjEaxV3rBYHysXZlQ8jtoFigS6PdM2KgoP2UPdnnKPSJBOCzoFPDo abu7S9hb/b9A2PfO8UZ9q4qNtGrpwItuc7fo7s6A= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:24 +0300 Message-Id: <20220517143325.71784-13-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 12/13] py: add geometry classes X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Add libcamera's geometry classes to the Python bindings. Note that this commit only adds the classes, but they are not used anywhere yet. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/libcamera/meson.build | 1 + src/py/libcamera/pygeometry.cpp | 119 ++++++++++++++++++++++++++++++++ src/py/libcamera/pymain.cpp | 2 + 3 files changed, 122 insertions(+) create mode 100644 src/py/libcamera/pygeometry.cpp diff --git a/src/py/libcamera/meson.build b/src/py/libcamera/meson.build index 32e74504..0bef52c7 100644 --- a/src/py/libcamera/meson.build +++ b/src/py/libcamera/meson.build @@ -14,6 +14,7 @@ pybind11_dep = pybind11_proj.get_variable('pybind11_dep') pycamera_sources = files([ 'pyenums.cpp', + 'pygeometry.cpp', 'pymain.cpp', ]) diff --git a/src/py/libcamera/pygeometry.cpp b/src/py/libcamera/pygeometry.cpp new file mode 100644 index 00000000..d77de144 --- /dev/null +++ b/src/py/libcamera/pygeometry.cpp @@ -0,0 +1,119 @@ +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright (C) 2022, Tomi Valkeinen + * + * Python bindings - Geometry classes + */ + +#include + +#include +#include + +#include +#include +#include + +namespace py = pybind11; + +using namespace libcamera; + +void init_pygeometry(py::module &m) +{ + auto pyPoint = py::class_(m, "Point"); + auto pySize = py::class_(m, "Size"); + auto pySizeRange = py::class_(m, "SizeRange"); + auto pyRectangle = py::class_(m, "Rectangle"); + + pyPoint + .def(py::init<>()) + .def(py::init()) + .def_readwrite("x", &Point::x) + .def_readwrite("y", &Point::y) + .def(py::self == py::self) + .def(-py::self) + .def("__str__", &Point::toString) + .def("__repr__", [](const Point &self) { + return py::str("libcamera.Point({}, {})") + .format(self.x, self.y); + }); + + pySize + .def(py::init<>()) + .def(py::init()) + .def_readwrite("width", &Size::width) + .def_readwrite("height", &Size::height) + .def_property_readonly("is_null", &Size::isNull) + .def("align_down_to", &Size::alignDownTo) + .def("align_up_to", &Size::alignUpTo) + .def("bound_to", &Size::boundTo) + .def("expand_to", &Size::expandTo) + .def("grow_by", &Size::growBy) + .def("shrink_by", &Size::shrinkBy) + .def("aligned_up_to", &Size::alignedUpTo) + .def("aligned_up_to", &Size::alignedUpTo) + .def("bounded_to", &Size::boundedTo) + .def("expanded_to", &Size::expandedTo) + .def("grown_by", &Size::grownBy) + .def("shrunk_by", &Size::shrunkBy) + .def("bounded_to_aspect_ratio", &Size::boundedToAspectRatio) + .def("expanded_to_aspect_ratio", &Size::expandedToAspectRatio) + .def("centered_to", &Size::centeredTo) + .def(py::self == py::self) + .def(py::self < py::self) + .def(py::self <= py::self) + .def(py::self * float()) + .def(py::self / float()) + .def(py::self *= float()) + .def(py::self /= float()) + .def("__str__", &Size::toString) + .def("__repr__", [](const Size &self) { + return py::str("libcamera.Size({}, {})") + .format(self.width, self.height); + }); + + pySizeRange + .def(py::init<>()) + .def(py::init()) + .def(py::init()) + .def(py::init()) + .def_readwrite("min", &SizeRange::min) + .def_readwrite("max", &SizeRange::max) + .def_readwrite("hStep", &SizeRange::hStep) + .def_readwrite("vStep", &SizeRange::vStep) + .def("contains", &SizeRange::contains) + .def(py::self == py::self) + .def("__str__", &SizeRange::toString) + .def("__repr__", [](const SizeRange &self) { + return py::str("libcamera.SizeRange(({}, {}), ({}, {}), {}, {})") + .format(self.min.width, self.min.height, + self.max.width, self.max.height, + self.hStep, self.vStep); + }); + + pyRectangle + .def(py::init<>()) + .def(py::init()) + .def(py::init()) + .def(py::init()) + .def_readwrite("x", &Rectangle::x) + .def_readwrite("y", &Rectangle::y) + .def_readwrite("width", &Rectangle::width) + .def_readwrite("height", &Rectangle::height) + .def_property_readonly("is_null", &Rectangle::isNull) + .def_property_readonly("center", &Rectangle::center) + .def_property_readonly("size", &Rectangle::size) + .def_property_readonly("topLeft", &Rectangle::topLeft) + .def("scale_by", &Rectangle::scaleBy) + .def("translate_by", &Rectangle::translateBy) + .def("bounded_to", &Rectangle::boundedTo) + .def("enclosed_in", &Rectangle::enclosedIn) + .def("scaled_by", &Rectangle::scaledBy) + .def("translated_by", &Rectangle::translatedBy) + .def(py::self == py::self) + .def("__str__", &Rectangle::toString) + .def("__repr__", [](const Rectangle &self) { + return py::str("libcamera.Rectangle({}, {}, {}, {})") + .format(self.x, self.y, self.width, self.height); + }); +} diff --git a/src/py/libcamera/pymain.cpp b/src/py/libcamera/pymain.cpp index 97b05903..96333ebc 100644 --- a/src/py/libcamera/pymain.cpp +++ b/src/py/libcamera/pymain.cpp @@ -137,11 +137,13 @@ static void handleRequestCompleted(Request *req) void init_pyenums(py::module &m); void init_pyenums_generated(py::module &m); +void init_pygeometry(py::module &m); PYBIND11_MODULE(_libcamera, m) { init_pyenums(m); init_pyenums_generated(m); + init_pygeometry(m); /* Forward declarations */ From patchwork Tue May 17 14:33:25 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tomi Valkeinen X-Patchwork-Id: 15937 Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 1FB80C3273 for ; Tue, 17 May 2022 14:34:05 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 96F646566D; Tue, 17 May 2022 16:34:04 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1652798044; bh=1+OP/vJ7T6H20/C4248xIS69yVugXiNvae2Aa5nEre4=; h=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=ku7bNdd4bqpejRs9AINRKh708amcI6zKntG+bFlbXhOhD0YV73mwxWILRFVVo+LBS l9cV83FYkDm5w559WtGhYY2ND26X1ZtCtEBgUYdhKeoVvdghDITnI59dopp9ULc64e D2Gzv6oWzpolZb/KVTfaPFfldTUE3Z3LdpYP9zoRcLqzGaNo48G3cU1+WYE9uV0aeQ 4tihtJIsnzoborcOmDzlQsp/5m3MuVVDjjhkkKe5uZ3boE/nLhRSJGQHIKZ17c7zM8 OvM/3N+sMlwunNr33D7ldLALTAAPRXIjQxVjSzpBWwaboEq9VWrFerT6RFbjkuR/M3 KJ1h59KT3plXA== Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 5D7216567E for ; Tue, 17 May 2022 16:33:58 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="dEAya37I"; dkim-atps=neutral Received: from deskari.lan (91-156-85-209.elisa-laajakaista.fi [91.156.85.209]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id C61838E6; Tue, 17 May 2022 16:33:57 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1652798038; bh=1+OP/vJ7T6H20/C4248xIS69yVugXiNvae2Aa5nEre4=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=dEAya37IirSW9tmdFjHO+qrkjMbI8D2IDcjqWKgokN420YdS0nB0QTxwHtIychVdE 2cPj71nH+Yv8A/EQQh5Nc6499I19QI9+f8ZfUIq4UYU235UNjL1o6USts0sdVsaB0k 0WtJtLuAV5P5G/fiMwO0sRAPGPa9b4CVz3AMPDPQ= To: libcamera-devel@lists.libcamera.org, David Plowman , Kieran Bingham , Laurent Pinchart , Jacopo Mondi Date: Tue, 17 May 2022 17:33:25 +0300 Message-Id: <20220517143325.71784-14-tomi.valkeinen@ideasonboard.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> References: <20220517143325.71784-1-tomi.valkeinen@ideasonboard.com> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v2 13/13] py: use geometry classes X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Tomi Valkeinen via libcamera-devel From: Tomi Valkeinen Reply-To: Tomi Valkeinen Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Now that we have proper geometry classes in the Python bindings, change the existing bindings and the .py files accordingly. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart Reviewed-by: Kieran Bingham --- src/py/cam/cam.py | 7 +++++-- src/py/cam/cam_kms.py | 3 ++- src/py/cam/cam_qt.py | 7 ++++--- src/py/cam/cam_qtgl.py | 3 ++- src/py/libcamera/pymain.cpp | 41 ++++++++----------------------------- 5 files changed, 22 insertions(+), 39 deletions(-) diff --git a/src/py/cam/cam.py b/src/py/cam/cam.py index 001fb9de..2f0690b5 100755 --- a/src/py/cam/cam.py +++ b/src/py/cam/cam.py @@ -160,8 +160,11 @@ def configure(ctx): for idx, stream_opts in enumerate(streams): stream_config = camconfig.at(idx) - if 'width' in stream_opts and 'height' in stream_opts: - stream_config.size = (stream_opts['width'], stream_opts['height']) + if 'width' in stream_opts: + stream_config.size.width = stream_opts['width'] + + if 'height' in stream_opts: + stream_config.size.height = stream_opts['height'] if 'pixelformat' in stream_opts: stream_config.pixel_format = libcam.PixelFormat(stream_opts['pixelformat']) diff --git a/src/py/cam/cam_kms.py b/src/py/cam/cam_kms.py index 04381da1..74cd3b38 100644 --- a/src/py/cam/cam_kms.py +++ b/src/py/cam/cam_kms.py @@ -126,7 +126,8 @@ class KMSRenderer: }) for fb in ctx['allocator'].buffers(stream): - w, h = cfg.size + w = cfg.size.width + h = cfg.size.height fds = [] strides = [] offsets = [] diff --git a/src/py/cam/cam_qt.py b/src/py/cam/cam_qt.py index 45a30aeb..91be2a08 100644 --- a/src/py/cam/cam_qt.py +++ b/src/py/cam/cam_qt.py @@ -84,8 +84,8 @@ def demosaic(data, r0, g0, g1, b0): def to_rgb(fmt, size, data): - w = size[0] - h = size[1] + w = size.width + h = size.height fmt = str(fmt) @@ -292,7 +292,8 @@ class MainWindow(QtWidgets.QWidget): def buf_to_qpixmap(self, stream, fb): with fb.mmap() as mfb: cfg = stream.configuration - w, h = cfg.size + w = cfg.size.width + h = cfg.size.height pitch = cfg.stride if str(cfg.pixel_format) == 'MJPEG': diff --git a/src/py/cam/cam_qtgl.py b/src/py/cam/cam_qtgl.py index 261accb8..4bbcda6c 100644 --- a/src/py/cam/cam_qtgl.py +++ b/src/py/cam/cam_qtgl.py @@ -268,7 +268,8 @@ class MainWindow(QtWidgets.QWidget): def create_texture(self, stream, fb): cfg = stream.configuration fmt = cfg.pixel_format.fourcc - w, h = cfg.size + w = cfg.size.width + h = cfg.size.height attribs = [ EGL_WIDTH, w, diff --git a/src/py/libcamera/pymain.cpp b/src/py/libcamera/pymain.cpp index 96333ebc..ef3f157a 100644 --- a/src/py/libcamera/pymain.cpp +++ b/src/py/libcamera/pymain.cpp @@ -6,7 +6,6 @@ */ /* - * \todo Add geometry classes (Point, Rectangle...) * \todo Add bindings for the ControlInfo class */ @@ -61,11 +60,11 @@ static py::object controlValueToPy(const ControlValue &cv) return py::cast(cv.get()); case ControlTypeRectangle: { const Rectangle *v = reinterpret_cast(cv.data().data()); - return py::make_tuple(v->x, v->y, v->width, v->height); + return py::cast(v); } case ControlTypeSize: { const Size *v = reinterpret_cast(cv.data().data()); - return py::make_tuple(v->width, v->height); + return py::cast(v); } case ControlTypeNone: default: @@ -99,14 +98,10 @@ static ControlValue pyToControlValue(const py::object &ob, ControlType type) return controlValueMaybeArray(ob); case ControlTypeString: return ControlValue(ob.cast()); - case ControlTypeRectangle: { - auto array = ob.cast>(); - return ControlValue(Rectangle(array[0], array[1], array[2], array[3])); - } - case ControlTypeSize: { - auto array = ob.cast>(); - return ControlValue(Size(array[0], array[1])); - } + case ControlTypeRectangle: + return ControlValue(ob.cast()); + case ControlTypeSize: + return ControlValue(ob.cast()); case ControlTypeNone: default: throw std::runtime_error("Control type not implemented"); @@ -397,15 +392,7 @@ PYBIND11_MODULE(_libcamera, m) .def("__str__", &StreamConfiguration::toString) .def_property_readonly("stream", &StreamConfiguration::stream, py::return_value_policy::reference_internal) - .def_property( - "size", - [](StreamConfiguration &self) { - return std::make_tuple(self.size.width, self.size.height); - }, - [](StreamConfiguration &self, std::tuple size) { - self.size.width = std::get<0>(size); - self.size.height = std::get<1>(size); - }) + .def_readwrite("size", &StreamConfiguration::size) .def_readwrite("pixel_format", &StreamConfiguration::pixelFormat) .def_readwrite("stride", &StreamConfiguration::stride) .def_readwrite("frame_size", &StreamConfiguration::frameSize) @@ -416,18 +403,8 @@ PYBIND11_MODULE(_libcamera, m) pyStreamFormats .def_property_readonly("pixel_formats", &StreamFormats::pixelformats) - .def("sizes", [](StreamFormats &self, const PixelFormat &pixelFormat) { - std::vector> fmts; - for (const auto &s : self.sizes(pixelFormat)) - fmts.push_back(std::make_tuple(s.width, s.height)); - return fmts; - }) - .def("range", [](StreamFormats &self, const PixelFormat &pixelFormat) { - const auto &range = self.range(pixelFormat); - return make_tuple(std::make_tuple(range.hStep, range.vStep), - std::make_tuple(range.min.width, range.min.height), - std::make_tuple(range.max.width, range.max.height)); - }); + .def("sizes", &StreamFormats::sizes) + .def("range", &StreamFormats::range); pyFrameBufferAllocator .def(py::init>(), py::keep_alive<1, 2>())