[libcamera-devel] [PATCH v1 1/2] pipeline: raspberrypi: Move sensor entity detection out of registerCamera()

Kieran Bingham kieran.bingham at ideasonboard.com
Wed Dec 8 13:14:17 CET 2021


Quoting Naushir Patuck (2021-12-01 11:57:10)
> Enumerate the sensor device entities in PipelineHandlerRPi::match() and loop
> over PipelineHandlerRPi::registerCamera() for each sensor found. This will
> allow the pipeline handler to register multiple cameras attached to a single
> Unicam instance with a Video Mux device.
> 
> Signed-off-by: Naushir Patuck <naush at raspberrypi.com>

This sounds like a really interesting use case/demonstration of how MC
exposes the hardware to userspace to do something useful with it. Even
before personally I'd struggled with the extra complexitys that MC
brings, so I'm glad to be seeing some of the 'benefits' it
facilitates...

Reviewed-by: Kieran Bingham <kieran.bingham at ideasonboard.com>

> ---
>  .../pipeline/raspberrypi/raspberrypi.cpp      | 35 +++++++++++--------
>  1 file changed, 20 insertions(+), 15 deletions(-)
> 
> diff --git a/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp b/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp
> index e31fa3b23859..811160490f5c 100644
> --- a/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp
> +++ b/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp
> @@ -314,7 +314,7 @@ private:
>                 return static_cast<RPiCameraData *>(camera->_d());
>         }
>  
> -       int registerCamera(MediaDevice *unicam, MediaDevice *isp);
> +       int registerCamera(MediaDevice *unicam, MediaDevice *isp, MediaEntity *sensorEntity);
>         int queueAllBuffers(Camera *camera);
>         int prepareBuffers(Camera *camera);
>         void freeBuffers(Camera *camera);
> @@ -1009,16 +1009,28 @@ bool PipelineHandlerRPi::match(DeviceEnumerator *enumerator)
>                 return false;
>         }
>  
> -       int ret = registerCamera(unicamDevice, ispDevice);
> -       if (ret) {
> -               LOG(RPI, Error) << "Failed to register camera: " << ret;
> -               return false;
> +       /*
> +        * The loop below is used to register multiple cameras behind one or more
> +        * video mux devices that are attaced to a particular Unicam instance.
> +        * Obviously these cameras cannot be used simultaneously.
> +        */
> +       unsigned int numCameras = 0;
> +       for (MediaEntity *entity : unicamDevice->entities()) {
> +               if (entity->function() != MEDIA_ENT_F_CAM_SENSOR)
> +                       continue;
> +
> +               int ret = registerCamera(unicamDevice, ispDevice, entity);
> +               if (ret)
> +                       LOG(RPI, Error) << "Failed to register camera "
> +                                       << entity->name() << ": " << ret;
> +               else
> +                       numCameras++;
>         }
>  
> -       return true;
> +       return !!numCameras;
>  }
>  
> -int PipelineHandlerRPi::registerCamera(MediaDevice *unicam, MediaDevice *isp)
> +int PipelineHandlerRPi::registerCamera(MediaDevice *unicam, MediaDevice *isp, MediaEntity *sensorEntity)
>  {
>         std::unique_ptr<RPiCameraData> data = std::make_unique<RPiCameraData>(this);
>  
> @@ -1059,14 +1071,7 @@ int PipelineHandlerRPi::registerCamera(MediaDevice *unicam, MediaDevice *isp)
>         data->isp_[Isp::Output1].dev()->bufferReady.connect(data.get(), &RPiCameraData::ispOutputDequeue);
>         data->isp_[Isp::Stats].dev()->bufferReady.connect(data.get(), &RPiCameraData::ispOutputDequeue);
>  
> -       /* Identify the sensor. */
> -       for (MediaEntity *entity : unicam->entities()) {
> -               if (entity->function() == MEDIA_ENT_F_CAM_SENSOR) {
> -                       data->sensor_ = std::make_unique<CameraSensor>(entity);
> -                       break;
> -               }
> -       }
> -
> +       data->sensor_ = std::make_unique<CameraSensor>(sensorEntity);
>         if (!data->sensor_)
>                 return -EINVAL;
>  
> -- 
> 2.25.1
>


More information about the libcamera-devel mailing list