From patchwork Thu Sep 8 18:48:40 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Xavier Roumegue X-Patchwork-Id: 17346 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 59AEBC3272 for ; Thu, 8 Sep 2022 18:49:25 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 07D7F620B3; Thu, 8 Sep 2022 20:49:24 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org; s=mail; t=1662662964; bh=o187exn0iRru3cc77DWztNSBQqaSJ8ZbzcWssCaAtw0=; 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=0ICSR3QmKsYb6cROVRV7Bc4ruvfGmOaVMOFfMLL/eThz+BpjBpxqiUDYnaIK6MT7y 9RxVWBPK0EpYn825s4F+GSc/wr/cQz+JMdaiX7CVEYIkVSU4jWOvxaC3D0/edIeH8w t3eT4ysgSIZjCh602p2xiHYt6z3OkcXZBFEO/I9lJVxGtQ2s+BMnuts4mK81uhalEf NOhVdu9//j++t+nvy2P1qBKg3sUCk3DOd02g/g+fzgMfjXKSULlzjx54lke8+uF5Mp Azp4La7KDOCuegZMtPw+9I6LtzkOA5R5ctIoZ8/PNiQV2/94dUA98b9LKZr2aRZgy8 3MHRwNKbBiSJg== Received: from EUR04-DB3-obe.outbound.protection.outlook.com (mail-eopbgr60064.outbound.protection.outlook.com [40.107.6.64]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 0F1BA620AF for ; Thu, 8 Sep 2022 20:49:20 +0200 (CEST) Authentication-Results: lancelot.ideasonboard.com; dkim=pass (1024-bit key; unprotected) header.d=NXP1.onmicrosoft.com header.i=@NXP1.onmicrosoft.com header.b="YGayduta"; dkim-atps=neutral ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=dlQAc/s+UUt6lhunECAVEFqHGWYL0tBXJfYwiOr2IcLqHHuK4voTb6VDXOPr6EGGDXgmcemOTtaQEYMkrE9HLRiJve7lzqk7mOoZPO36FexQz+kBQlewHiWEG43dH7RR5H0GYL8yfY+ff2nC2VzMvYxuOleuGfdMgUEUGPWlwLlcmx0FE3oCzdqRuwGLmrXGsYFYqA0vGN3LwcHtbW2YzIlwBhpjGWd0fK/66JCIeojwazjsZz386PEiGEMKMZwbTr0FKRnn6QHqgtynHWVootCxlCKeGF6nt9igmXfdidnFO2X9y64EeB7sbDT7dFqE2joFSvfql4BR9a/4Anu0xQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=S2sNuxMIzSdlEJJoNgfqntq4XAIKjQDfb11cjwNMjfE=; b=f8X5JZCJakiVnt6hWg5a2hbdG3bPLcb4hxf6+d0Ygbw2EoxXs1GJRWuWl2h+lmc7kkfxxxGAi1MStjqRAofk356CCfBycrsrn3jis1Nh+Pxxu0P2qrIxlzmEvGeyaUvgaeoBbGC0YgY7qA2U5pJhgn1ShXxkfi9zVqJ1k2CmKVPVf+OZPgfo78/Qv7O7/dC9dv/l2xNLmZN801R9/vQLuVrvkBcKop55886slGxeErEe/nkvGN2/QyxdtzpuBgAqRZYe2ldNlib1Pj67S4GOhpU1Owwk0Y6TOulJGiltFKNmKI3BUjAxFKnS3USUG2MEXH91kdtNdtYehJ+wMhIuBg== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=oss.nxp.com; dmarc=pass action=none header.from=oss.nxp.com; dkim=pass header.d=oss.nxp.com; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=NXP1.onmicrosoft.com; s=selector2-NXP1-onmicrosoft-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=S2sNuxMIzSdlEJJoNgfqntq4XAIKjQDfb11cjwNMjfE=; b=YGaydutaSbmy0wHv7HpWPlFbwESZw51OzGwAsoo1yyO4rT5zHmY6c5bn6MCeBUOHAiTk+zmT6zl7NHwvotxtG6wkaVgvmIYqx5ERodL5rstm6pewLZncBK1gvkKvPKjy7G3IExDWNjRoN9qk5aYRxTmI66UIPInWpcWhyRloGz0= Authentication-Results: dkim=none (message not signed) header.d=none;dmarc=none action=none header.from=oss.nxp.com; Received: from PAXPR04MB8703.eurprd04.prod.outlook.com (2603:10a6:102:21e::22) by AS8PR04MB8852.eurprd04.prod.outlook.com (2603:10a6:20b:42f::14) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.5612.19; Thu, 8 Sep 2022 18:49:18 +0000 Received: from PAXPR04MB8703.eurprd04.prod.outlook.com ([fe80::485:adba:7081:715a]) by PAXPR04MB8703.eurprd04.prod.outlook.com ([fe80::485:adba:7081:715a%3]) with mapi id 15.20.5612.019; Thu, 8 Sep 2022 18:49:18 +0000 To: libcamera-devel@lists.libcamera.org Date: Thu, 8 Sep 2022 20:48:40 +0200 Message-Id: <20220908184850.1874303-5-xavier.roumegue@oss.nxp.com> X-Mailer: git-send-email 2.37.3 In-Reply-To: <20220908184850.1874303-1-xavier.roumegue@oss.nxp.com> References: <20220908184850.1874303-1-xavier.roumegue@oss.nxp.com> X-ClientProxiedBy: PR3P250CA0001.EURP250.PROD.OUTLOOK.COM (2603:10a6:102:57::6) To PAXPR04MB8703.eurprd04.prod.outlook.com (2603:10a6:102:21e::22) MIME-Version: 1.0 X-MS-Exchange-MessageSentRepresentingType: 1 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: PAXPR04MB8703:EE_|AS8PR04MB8852:EE_ X-MS-Office365-Filtering-Correlation-Id: 1092cc32-246a-40ce-11c8-08da91cad5e5 X-MS-Exchange-SharedMailbox-RoutingAgent-Processed: True X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0; X-Microsoft-Antispam-Message-Info: Mb93W/cwXJp1AnF/HRP3h/f5BJcJOAr6NaVFuGNAh6iaIwfzl8RA1yAdKfjefb4jMUbk7OF0W8ekYcZC4X1PVQYk8vYlNPb3TKweG2IM77wr9HRlKx/BvOZnuqRxUb90S8jQ/lATvoVxi36JelZwL9EIcMBYVzghaqsh5p1J/rCJKrxQo4R6daFWJAoC01eqOiVtqq04v5NPe9UOHkaw/+MdyMAqadoHHk63OKtqU/cV0CkKUd9UgNA8oQAqUa+Mpsik1BRLXDpUSwNRVOpwIXYZzq1ka5Do7Jaup/2swAqdJ00NigVCqwhsyGsW8L3SHwNRXWZOfpVpSDAeyChF/4/Y+qebWZbDRSmXKs9hfUlYpvkGIv0UPK5JSAQB4cbOlYA4gLFOpAPeheCW5h5vyzfFPaoJvRq8qpVovWWyPNoqRBL236hbbBXljAnL1GwbCTeFHUTkTIXori02HSD8dAnx3knJJRaUyM+ihgCWzSzfVRoEY14NPU0qsra6QkyAO+4r+BIRIAHSYq6I9UwGx+xH37myAoXcVIzJwysjj9a3CMmYV6FLxDpofkAMO94XYzqnbBYGNCB18ahpvyhnvdKRCC+LVHbQf2PI8XUhqPSFmhVFTdWqcxUJPkQp4pTo2puE4w58oLeTt91/PmHvKxeUvd+RmGlJxxwRPqjND2XcHOL29vxPXwKgG1dPb1es7lEiyNJE4ebOdNBF25RhHZxElKTBx7rjKloM8bw2JfNw2AhHEId342T+Ivb+PuYl5PfmD6Qfp/ior5gNTF9dNg== X-Forefront-Antispam-Report: CIP:255.255.255.255; CTRY:; LANG:en; SCL:1; SRV:; IPV:NLI; SFV:NSPM; H:PAXPR04MB8703.eurprd04.prod.outlook.com; PTR:; CAT:NONE; SFS:(13230016)(4636009)(39860400002)(346002)(376002)(396003)(136003)(366004)(38100700002)(66556008)(66476007)(66946007)(8936002)(44832011)(5660300002)(4326008)(8676002)(6916009)(316002)(41300700001)(186003)(1076003)(2616005)(2906002)(478600001)(6666004)(86362001)(6512007)(52116002)(6506007)(83380400001)(6486002)(41533002); DIR:OUT; SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: btF8Hl4mui7pFKKzpKKrewkpqlMwEZusPbSts9EZu6l2Y1z9X9n6f36PwMNFjQoMglvq6P6+hltOfLnIL9hjVuHoP2lG8bPnM9iDtEiUN3dTyqxPSgig/GgIwvaVgcJo2EVr95ic8UytL5+5eOuyLO7WZGWQmDVvukUwQTTs1D0HtcJPhwtd+/68moiSruGVoo+dgWY6DHOYvrE4vnjTnWaHuoPo23GLZZZ2SugMxdXcop2akKM0KpUgd9fjb8UJDH/0p1MQ7YwV4pVOJf/Ims1M7mbKFynM/If4SjH0Yo90v8cKV0dDOMRP70+pce1jxYFOrNfaNKT7wm+t6CJxdnqRQ0UJiNO3HPM0wV+vdwAyuCc6mR1sKuQjgKYi3nzaJ5H1mykTRRTaVeZfv0uaQzofaSm8xkU+Ut5/tenakd7NIEQg8NvG4Et2mFDat5A0xI4SOJN15seiGhLQvQNCt3HZZYFE7xT0xB9+6meF/FS+ybFWurUzjkPnhICZFyKDzI20AE2MVwXEPv/8rYUIUQ1cCCqz1DjUEcD9QyRuFU7QR+da/pStvUrzroj/njMeMJTGY5sv2I9h7eGhr7+AQq/MhZIiu4cjuUQOf6miWSU4ygZ1/kped1iZxkSEB7Pdn4GLd/cOpnwSM8fugBCjsy8AL33wtReRo0xqjnb9d+Q8KgmMB6H/1/Bpn5sSJFgAVevzXZm4YdHcrpRyacBprt/jekWGfE80TP/fCPxlCZ3ty/fF9L+kfEPsUs9ufRJlhQXepsopQW1JMYz82emg9vAp+RgKkkl7dev0p6yczOiPG58M/UqxAS7FYJLdL93oysrzoOg2S1W1qjcacpO8ZiVOxQ7kKSF6Tq644ZyoU0mOG6o6OBCsUuk0zV47HlWjGLDiLF3FRgFW1UvlbiypYd4N15hzRXOqIPcfDdBBlj6thCKIV1LUz38uCUbY555kKf1g806SJLb32v5KTQvrEAWP0WBG7ETe8Iieng0x88X7HtqVZjF8mb+bi0L5rID91+LvlbBi2CzqbvEX/0mtmQu49pWilTmNFICoF7xffSDNOmWfXuTu4OQWFj3MwFBOKrh/cIR6EcTF+YZGRaIYAYsAWnXsxBRMrr180x8bfMC/ohCEOwEblAS/EVXlQx5glmRjibIxPl6crPoewn4tHPxqp78vrLuneyAYTkjd6+KGwIL94HnwmCW+jHaQYxfI6h4WOKBhZ9uiN1ES9jKxI5V8lYk841UdvvfELPZ6KlKcjfMVh0C7ysZrK/nkUqlWPfqTqOgQeOJuosrSTR1DZ1JewdHv6OWrrGFiBS81YVbjdzidDM2n1WnpWzOQsIS0ERlf6QHgOnodyJ56waa/tsm9yu1TYpS0B6MnoG/YONpVg4Gf5dvSUP2IYSCoPOvmxcQQOybgxFD0r/kY5vHsz7JDLwmhrfoGcZJuo5z+7rd8QaHuUibBRniiNicJwIIalUro39W7Tlv2CDlmbxtgxkH8RJfyG39XRNep5BJuTZfwOYjAwgRk637efOQ6SqKcN0Sv9mGo1I8RUQLLE+eCfa9nD3hAjuY8osAgXYbeEY+MtBqkrYjdl+Y9sIM1JZJDFFTwKIxCRTMVOIqL4jiDX/O7e5NprhMLuLqXKY8DaUzh0O3sSc0dC4mVQBZmA8hoORBB0vJEjQU0Ky+1UE70zQ== X-OriginatorOrg: oss.nxp.com X-MS-Exchange-CrossTenant-Network-Message-Id: 1092cc32-246a-40ce-11c8-08da91cad5e5 X-MS-Exchange-CrossTenant-AuthSource: PAXPR04MB8703.eurprd04.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-OriginalArrivalTime: 08 Sep 2022 18:49:18.6514 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 686ea1d3-bc2b-4c6f-a92c-d99c5c301635 X-MS-Exchange-CrossTenant-MailboxType: HOSTED X-MS-Exchange-CrossTenant-UserPrincipalName: 70jmuE66fDy2Nrv96o8VyotLDKG63ZKmwstpx6tfc9Akqh0S192QhbAsmuw0iM7fZnx9gHwtbge4JE6aBbENCw== X-MS-Exchange-Transport-CrossTenantHeadersStamped: AS8PR04MB8852 Subject: [libcamera-devel] [PATCH 04/14] libcamera: Declare generic size and format converter interface 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: Xavier Roumegue via libcamera-devel From: Xavier Roumegue Reply-To: Xavier Roumegue Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Declare a converter Abstract Base Class intented to provide generic interfaces to hardware offering size and format conversion services on streams. This is mainly based on the public interfaces of the current converter class implementation found in the simple pipeline handler. The main change is the introduction of load_configuration() method which can be used by the concrete implementation to load hardware specific runtime parameters defined by the application. Signed-off-by: Xavier Roumegue --- include/libcamera/internal/converter.h | 101 ++++++++++++++++++++++++ include/libcamera/internal/meson.build | 1 + src/libcamera/converter.cpp | 102 +++++++++++++++++++++++++ src/libcamera/meson.build | 1 + 4 files changed, 205 insertions(+) create mode 100644 include/libcamera/internal/converter.h create mode 100644 src/libcamera/converter.cpp diff --git a/include/libcamera/internal/converter.h b/include/libcamera/internal/converter.h new file mode 100644 index 00000000..e2237c57 --- /dev/null +++ b/include/libcamera/internal/converter.h @@ -0,0 +1,101 @@ +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright (C) 2020, Laurent Pinchart + * Copyright 2022 NXP + * + * converter.h - Generic stream converter infrastructure + */ + +#pragma once + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include + +namespace libcamera { + +class FrameBuffer; +class MediaDevice; +class Size; +class SizeRange; +struct StreamConfiguration; + +class Converter +{ +public: + Converter(MediaDevice *media); + virtual ~Converter(); + virtual int loadConfiguration(const std::string &filename) = 0; + + virtual bool isValid() const = 0; + + virtual std::vector formats(PixelFormat input) = 0; + virtual SizeRange sizes(const Size &input) = 0; + + virtual std::tuple + strideAndFrameSize(const PixelFormat &pixelFormat, const Size &size) = 0; + + virtual int configure(const StreamConfiguration &inputCfg, + const std::vector> &outputCfg) = 0; + virtual int exportBuffers(unsigned int ouput, unsigned int count, + std::vector> *buffers) = 0; + + virtual int start() = 0; + virtual void stop() = 0; + + virtual int queueBuffers(FrameBuffer *input, + const std::map &outputs) = 0; + + std::string deviceNode_; + Signal inputBufferReady; + Signal outputBufferReady; +}; + +class ConverterFactory +{ +public: + ConverterFactory(const std::string name); + virtual ~ConverterFactory() = default; + + static std::unique_ptr create(MediaDevice *media); + + static void registerType(ConverterFactory *factory); + static std::vector &factories(); + static std::vector names(); + +protected: + virtual Converter *createInstance(MediaDevice *media) = 0; + virtual const std::vector aliases() const = 0; + +private: + LIBCAMERA_DISABLE_COPY_AND_MOVE(ConverterFactory) + + std::string name_; +}; + +#define REGISTER_CONVERTER(name, converter, ...) \ + class converter##Factory final : public ConverterFactory \ + { \ + public: \ + converter##Factory() : ConverterFactory(name) {} \ + \ + private: \ + Converter *createInstance(MediaDevice *media) \ + { \ + return new converter(media); \ + } \ + std::vector aliases_ = { __VA_ARGS__ }; \ + const std::vector aliases() const { return aliases_; } \ + }; \ + static converter##Factory global_##converter##Factory; + +} /* namespace libcamera */ diff --git a/include/libcamera/internal/meson.build b/include/libcamera/internal/meson.build index 7a780d48..8f50d755 100644 --- a/include/libcamera/internal/meson.build +++ b/include/libcamera/internal/meson.build @@ -19,6 +19,7 @@ libcamera_internal_headers = files([ 'camera_sensor_properties.h', 'control_serializer.h', 'control_validator.h', + 'converter.h', 'delayed_controls.h', 'device_enumerator.h', 'device_enumerator_sysfs.h', diff --git a/src/libcamera/converter.cpp b/src/libcamera/converter.cpp new file mode 100644 index 00000000..89a594d1 --- /dev/null +++ b/src/libcamera/converter.cpp @@ -0,0 +1,102 @@ + +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright 2022 NXP + * + * converter.cpp - Generic Format converter interface + */ + +#include + +#include + +#include "libcamera/internal/converter.h" +#include "libcamera/internal/media_device.h" + +namespace libcamera { + +LOG_DEFINE_CATEGORY(Converter) + +Converter::Converter(MediaDevice *media) +{ + const std::vector &entities = media->entities(); + auto it = std::find_if(entities.begin(), entities.end(), + [](MediaEntity *entity) { + return entity->function() == MEDIA_ENT_F_IO_V4L; + }); + if (it == entities.end()) + return; + + deviceNode_ = (*it)->deviceNode(); +} + +Converter::~Converter() +{ +} + +ConverterFactory::ConverterFactory(const std::string name) + : name_(name) +{ + registerType(this); +} + +std::unique_ptr ConverterFactory::create(MediaDevice *media) +{ + std::vector &factories = + ConverterFactory::factories(); + + for (ConverterFactory *factory : factories) { + std::vector aliases = factory->aliases(); + auto it = std::find(aliases.begin(), aliases.end(), media->driver()); + + if (it == aliases.end() && media->driver() != factory->name_) + continue; + + LOG(Converter, Debug) + << "Creating converter from " + << factory->name_ << " factory with " + << (it == aliases.end() ? "no" : media->driver()) << " alias."; + + Converter *converter = factory->createInstance(media); + return std::unique_ptr(converter); + } + + return nullptr; +} + +void ConverterFactory::registerType(ConverterFactory *factory) +{ + std::vector &factories = + ConverterFactory::factories(); + + factories.push_back(factory); +} + +std::vector ConverterFactory::names() +{ + std::vector list; + + std::vector &factories = + ConverterFactory::factories(); + + for (ConverterFactory *factory : factories) { + list.push_back(factory->name_); + for (auto alias : factory->aliases()) + list.push_back(alias); + } + + return list; +} + +std::vector &ConverterFactory::factories() +{ + /* + * The static factories map is defined inside the function to ensure + * it gets initialized on first use, without any dependency on link + * order. + */ + static std::vector factories; + return factories; +} + +} /* namespace libcamera */ diff --git a/src/libcamera/meson.build b/src/libcamera/meson.build index 63b47b17..a261d4b4 100644 --- a/src/libcamera/meson.build +++ b/src/libcamera/meson.build @@ -13,6 +13,7 @@ libcamera_sources = files([ 'controls.cpp', 'control_serializer.cpp', 'control_validator.cpp', + 'converter.cpp', 'delayed_controls.cpp', 'device_enumerator.cpp', 'device_enumerator_sysfs.cpp',