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

Naushir Patuck naush at raspberrypi.com
Thu Dec 9 09:57:52 CET 2021


Hi Laurent,

Thank you for your feedback!

On Wed, 8 Dec 2021 at 18:40, Laurent Pinchart <
laurent.pinchart at ideasonboard.com> wrote:

> Hi Naush,
>
> Thank you for the patch.
>
> On Wed, Dec 08, 2021 at 03:15:26PM +0000, Naushir Patuck wrote:
> > 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>
> > 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 86851ac467ad..756878c70036 100644
> > --- a/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp
> > +++ b/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp
> > @@ -310,7 +310,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);
> > @@ -1029,16 +1029,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.
>
> s/attaced/attached/
>
> > +      * Obviously these cameras cannot be used simultaneously.
>
> We need to expose mutual exclusion between cameras to applications
> through the libcamera public API. It doesn't have to be a blocker for
> the series, but should be done soon after, otherwise trying to use both
> cameras will result in incorrect behaviour (and possibly even crashes).
> Have you given any thought to how this could be done ?
>

Is this not already handled in the Camera class?  If I have a mux with 2
devices
attached to a single Unicam instance, hence single pipeline handler, I
cannot
run camera in one process and camera 1 in another.  Camera::acquire() would
vail to lock the pipeline handler:

 if (!d->pipe_->lock()) {
    LOG(Camera, Info)
        << "Pipeline handler in use by another process";
    return -EBUSY;
}

Perhaps this long point should be turned into Error level? I get the same
result
if I try to run both cameras in a single process (e.g. with cam -c 1 -C -c
2 -C).


>
> > +      */
> > +     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++;
>
> I tend to deal with error first, but that's a personal preference:
>
>                 int ret = registerCamera(unicamDevice, ispDevice, entity);
>                 if (ret) {
>                         LOG(RPI, Error) << "Failed to register camera "
>                                         << entity->name() << ": " << ret;
>                         continue;
>                 }
>
>                 numCameras++;
>
> >       }
> >
> > -     return true;
> > +     return !!numCameras;
>
> This looks fine, but by itself may cause a regression. Patch 2/2 will be
> merged with this one, so the problem would only occur during bisection,
> but still, I think we should squash the two patches together.
>

I'm sure I am missing something obvious, but why would this patch in
isolation
cause a regression?  The only additional function gained here would be to
allow the pipeline handler to enumerate multiple cameras attached to a mux,
but not allow one of the cameras to be run - same as before this change :-)

Regards,
Naush


> >  }
> >
> > -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);
> >
> > @@ -1079,14 +1091,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;
> >
>
> --
> Regards,
>
> Laurent Pinchart
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.libcamera.org/pipermail/libcamera-devel/attachments/20211209/81e8e47f/attachment.htm>


More information about the libcamera-devel mailing list