/* SPDX-License-Identifier: LGPL-2.1-or-later */ /* * Copyright (C) 2018, Google Inc. * * Pipeline handler infrastructure */ #pragma once #include #include #include #include #include #include #include #include "libcamera/internal/camera_manager.h" #include "libcamera/internal/ipa_manager.h" namespace libcamera { class Camera; class CameraConfiguration; class DeviceEnumerator; class DeviceMatch; class FrameBuffer; class MediaDevice; class PipelineHandler; class Request; class PipelineHandler : public std::enable_shared_from_this, public Object { public: PipelineHandler(CameraManager *manager, unsigned int maxQueuedRequestsDevice = 32); virtual ~PipelineHandler(); virtual bool match(DeviceEnumerator *enumerator) = 0; std::shared_ptr acquireMediaDevice(DeviceEnumerator *enumerator, const DeviceMatch &dm); bool acquire(Camera *camera); void release(Camera *camera); virtual std::unique_ptr generateConfiguration(Camera *camera, Span roles) = 0; virtual int configure(Camera *camera, CameraConfiguration *config) = 0; virtual int exportFrameBuffers(Camera *camera, Stream *stream, std::vector> *buffers) = 0; virtual int start(Camera *camera, const ControlList *controls) = 0; void stop(Camera *camera); bool hasPendingRequests(const Camera *camera) const; void registerRequest(Request *request); void queueRequest(Request *request); bool completeBuffer(Request *request, FrameBuffer *buffer); void completeRequest(Request *request); void cancelRequest(Request *request); std::string configurationFile(const std::string &subdir, const std::string &name, bool silent = false) const; const char *name() const { return name_; } CameraManager *cameraManager() const { return manager_; } template std::unique_ptr createIPA(uint32_t minVersion, uint32_t maxVersion) { IPAManager *ipaManager = manager_->_d()->ipaManager(); return ipaManager->createIPA(this, minVersion, maxVersion); } protected: void registerCamera(std::shared_ptr camera); void hotplugMediaDevice(std::shared_ptr media); unsigned int useCount() const { return useCount_; } virtual int queueRequestDevice(Camera *camera, Request *request) = 0; virtual void stopDevice(Camera *camera) = 0; virtual bool acquireDevice(Camera *camera); virtual void releaseDevice(Camera *camera); CameraManager *manager_; const unsigned int maxQueuedRequestsDevice_; private: void unlockMediaDevices(); void mediaDeviceDisconnected(std::shared_ptr media); virtual void disconnect(); void doQueueRequest(Request *request); void doQueueRequests(Camera *camera); std::vector> mediaDevices_; std::vector> cameras_; const char *name_; unsigned int useCount_; friend class PipelineHandlerFactoryBase; }; class PipelineHandlerFactoryBase { public: PipelineHandlerFactoryBase(const char *name); virtual ~PipelineHandlerFactoryBase() = default; std::shared_ptr create(CameraManager *manager) const; const std::string &name() const { return name_; } static std::vector &factories(); static const PipelineHandlerFactoryBase *getFactoryByName(const std::string &name); private: static void registerType(PipelineHandlerFactoryBase *factory); virtual std::unique_ptr createInstance(CameraManager *manager) const = 0; std::string name_; }; template class PipelineHandlerFactory final : public PipelineHandlerFactoryBase { public: PipelineHandlerFactory(const char *name) : PipelineHandlerFactoryBase(name) { } std::unique_ptr createInstance(CameraManager *manager) const override { return std::make_unique<_PipelineHandler>(manager); } }; #define REGISTER_PIPELINE_HANDLER(handler, name) \ static PipelineHandlerFactory global_##handler##Factory(name); } /* namespace libcamera */