diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/libcamera/pipeline/rkisp1/rkisp1.cpp | 86 |
1 files changed, 32 insertions, 54 deletions
diff --git a/src/libcamera/pipeline/rkisp1/rkisp1.cpp b/src/libcamera/pipeline/rkisp1/rkisp1.cpp index 194dfce7..675f0a74 100644 --- a/src/libcamera/pipeline/rkisp1/rkisp1.cpp +++ b/src/libcamera/pipeline/rkisp1/rkisp1.cpp @@ -42,6 +42,7 @@ #include "libcamera/internal/framebuffer.h" #include "libcamera/internal/ipa_manager.h" #include "libcamera/internal/media_device.h" +#include "libcamera/internal/media_pipeline.h" #include "libcamera/internal/pipeline_handler.h" #include "libcamera/internal/v4l2_subdevice.h" #include "libcamera/internal/v4l2_videodevice.h" @@ -116,6 +117,11 @@ public: ControlInfoMap ipaControls_; + /* + * All entities in the pipeline, from the camera sensor to the RKISP1. + */ + MediaPipeline pipe_; + private: void paramsComputed(unsigned int frame, unsigned int bytesused); void setSensorControls(unsigned int frame, @@ -180,8 +186,7 @@ private: friend RkISP1CameraConfiguration; friend RkISP1Frames; - int initLinks(Camera *camera, const CameraSensor *sensor, - const RkISP1CameraConfiguration &config); + int initLinks(Camera *camera, const RkISP1CameraConfiguration &config); int createCamera(MediaEntity *sensor); void tryCompleteRequest(RkISP1FrameInfo *info); void imageBufferReady(FrameBuffer *buffer); @@ -199,7 +204,6 @@ private: std::unique_ptr<V4L2Subdevice> isp_; std::unique_ptr<V4L2VideoDevice> param_; std::unique_ptr<V4L2VideoDevice> stat_; - std::unique_ptr<V4L2Subdevice> csi_; bool hasSelfPath_; bool isRaw_; @@ -223,8 +227,6 @@ private: std::queue<FrameBuffer *> availableStatBuffers_; Camera *activeCamera_; - - const MediaPad *ispSink_; }; RkISP1Frames::RkISP1Frames(PipelineHandler *pipe) @@ -798,7 +800,7 @@ int PipelineHandlerRkISP1::configure(Camera *camera, CameraConfiguration *c) CameraSensor *sensor = data->sensor_.get(); int ret; - ret = initLinks(camera, sensor, *config); + ret = initLinks(camera, *config); if (ret) return ret; @@ -821,12 +823,12 @@ int PipelineHandlerRkISP1::configure(Camera *camera, CameraConfiguration *c) LOG(RkISP1, Debug) << "Sensor configured with " << format; - if (csi_) { - ret = csi_->setFormat(0, &format); - if (ret < 0) - return ret; - } + /* Propagate format through the internal media pipeline up to the ISP */ + ret = data->pipe_.configure(sensor, &format); + if (ret < 0) + return ret; + LOG(RkISP1, Debug) << "Configuring ISP with : " << format; ret = isp_->setFormat(0, &format); if (ret < 0) return ret; @@ -1201,7 +1203,6 @@ int PipelineHandlerRkISP1::queueRequestDevice(Camera *camera, Request *request) */ int PipelineHandlerRkISP1::initLinks(Camera *camera, - const CameraSensor *sensor, const RkISP1CameraConfiguration &config) { RkISP1CameraData *data = cameraData(camera); @@ -1212,31 +1213,16 @@ int PipelineHandlerRkISP1::initLinks(Camera *camera, return ret; /* - * Configure the sensor links: enable the link corresponding to this - * camera. + * Configure the sensor links: enable the links corresponding to this + * pipeline all the way up to the ISP, through any connected CSI receiver. */ - for (MediaLink *link : ispSink_->links()) { - if (link->source()->entity() != sensor->entity()) - continue; - - LOG(RkISP1, Debug) - << "Enabling link from sensor '" - << link->source()->entity()->name() - << "' to ISP"; - - ret = link->setEnabled(true); - if (ret < 0) - return ret; - } - - if (csi_) { - MediaLink *link = isp_->entity()->getPadByIndex(0)->links().at(0); - - ret = link->setEnabled(true); - if (ret < 0) - return ret; + ret = data->pipe_.initLinks(); + if (ret) { + LOG(RkISP1, Error) << "Failed to set up pipe links"; + return ret; } + /* Configure the paths after the ISP */ for (const StreamConfiguration &cfg : config) { if (cfg.stream() == &data->mainPathStream_) ret = data->mainPath_->setEnabled(true); @@ -1312,6 +1298,13 @@ int PipelineHandlerRkISP1::createCamera(MediaEntity *sensor) std::make_unique<RkISP1CameraData>(this, &mainPath_, hasSelfPath_ ? &selfPath_ : nullptr); + /* Identify the pipeline path between the sensor and the rkisp1_isp */ + ret = data->pipe_.init(sensor, "rkisp1_isp"); + if (ret) { + LOG(RkISP1, Error) << "Failed to identify path from sensor to sink"; + return ret; + } + data->sensor_ = CameraSensorFactoryBase::create(sensor); if (!data->sensor_) return -ENODEV; @@ -1347,6 +1340,7 @@ int PipelineHandlerRkISP1::createCamera(MediaEntity *sensor) const std::string &id = data->sensor_->id(); std::shared_ptr<Camera> camera = Camera::create(std::move(data), id, streams); + registerCamera(std::move(camera)); return 0; @@ -1354,8 +1348,6 @@ int PipelineHandlerRkISP1::createCamera(MediaEntity *sensor) bool PipelineHandlerRkISP1::match(DeviceEnumerator *enumerator) { - const MediaPad *pad; - DeviceMatch dm("rkisp1"); dm.add("rkisp1_isp"); dm.add("rkisp1_resizer_mainpath"); @@ -1380,22 +1372,6 @@ bool PipelineHandlerRkISP1::match(DeviceEnumerator *enumerator) if (isp_->open() < 0) return false; - /* Locate and open the optional CSI-2 receiver. */ - ispSink_ = isp_->entity()->getPadByIndex(0); - if (!ispSink_ || ispSink_->links().empty()) - return false; - - pad = ispSink_->links().at(0)->source(); - if (pad->entity()->function() == MEDIA_ENT_F_VID_IF_BRIDGE) { - csi_ = std::make_unique<V4L2Subdevice>(pad->entity()); - if (csi_->open() < 0) - return false; - - ispSink_ = csi_->entity()->getPadByIndex(0); - if (!ispSink_) - return false; - } - /* Locate and open the stats and params video nodes. */ stat_ = V4L2VideoDevice::fromEntityName(media_, "rkisp1_stats"); if (stat_->open() < 0) @@ -1446,8 +1422,10 @@ bool PipelineHandlerRkISP1::match(DeviceEnumerator *enumerator) * camera instance for each of them. */ bool registered = false; - for (MediaLink *link : ispSink_->links()) { - if (!createCamera(link->source()->entity())) + + for (MediaEntity *entity : media_->locateEntities(MEDIA_ENT_F_CAM_SENSOR)) { + LOG(RkISP1, Debug) << "Identified " << entity->name(); + if (!createCamera(entity)) registered = true; } |