[libcamera-devel] [RFC PATCH] Documentation: IPU3 IPA Design guide

Kieran Bingham kieran.bingham at ideasonboard.com
Thu Sep 16 14:37:28 CEST 2021


Hi Laurent,

+cc JM for discussion point below...

On 14/09/2021 11:34, Laurent Pinchart wrote:
> Hi Kieran,
> 
> On Tue, Sep 14, 2021 at 11:13:39AM +0100, Kieran Bingham wrote:
>> On 14/09/2021 06:37, Laurent Pinchart wrote:
>>> On Sun, Sep 12, 2021 at 10:30:17PM +0100, Kieran Bingham wrote:
>>>> The IPU3 IPA implements the basic 3a using the ImgU ISP.
>>>
>>> s/3a/3A/
>>>
>>> Technically speaking we're only implementing 2 out of 3 at this point
>>> :-)
>>>
>>>> Provide an overview document to describe it's operations, and provide a
>>>
>>> s/it's/its/
>>>
>>>> block diagram to help visualise how the components are put together to
>>>> assist any new developers exploring the code.
>>>>
>>>> Signed-off-by: Kieran Bingham <kieran.bingham at ideasonboard.com>
>>>>
>>>> ---
>>>> This is really just an RFC: Particularly:
>>>>
>>>>  - Should this content actually live in Documentation?
>>>>    or is it more suited to a page under src/ipa/ipu3/...
>>>
>>> Good question. We tend to document things in the code where possible.
>>> Would there be any drawback from doing so in this case ?
>>
>> I don't think so - I think the question mostly comes from
>> 'discoverability' of the documentation.
>>
>>
>> Which is also a bigger question that we need to make it easier for
>> readers to find the documentation that they desire.
>>
>> I've come across a great talk on this recently:
>>   - What nobody tells you about documentation - Daniele Procida
>>   - PyConAu
>>   - https://2017.pycon-au.org/schedule/presentation/15/
>>   - https://youtu.be/t4vKPhjcMZg
>>
>> And that's been spun into a website to document how to document ;-)
>>   - https://diataxis.fr/
> 
> Thanks, I'll have a look.
> 
>> So, I think this could indeed live under src/ipa/ipu3 but it needs to be
>> clear that this should be the first thing to read when looking into the IPA.
> 
> Agreed. I could envision moving it to Documentation/ later, as part of a
> longer document that uses the IPU3 IPA to teach how to write algorithms,
> but at that point we'll start writing a book about algorithm design :-)

For now, for the v2 I will keep this as an RST document, but place it in
src/ipa/ipu3/.


>>>>  - This is not complete to document all functionality
>>>>    but gives an overview of the current implementation
>>>
>>> Sounds good to me.
>>>
>>>>  - Is there anything anyone would find helpful for me to
>>>>    extend/write about on this?
>>>>
>>>>  - It could likely get merged in with some of the work
>>>>    that Jean-Michel is doing, and might duplicate some of
>>>>    the parts he is documenting, but this was an aim to
>>>>    write a single page overview as a getting started with
>>>>    the IPU3 IPA ....
>>>
>>> I think it's *very* useful to have an overview.

I'll keep this separate for now then.

>>>
>>>>  .../guides/ipu3-ipa-design-guide.rst          | 144 ++++++++++++++++++
>>>>  1 file changed, 144 insertions(+)
>>>>  create mode 100644 Documentation/guides/ipu3-ipa-design-guide.rst
>>>>
>>>> diff --git a/Documentation/guides/ipu3-ipa-design-guide.rst b/Documentation/guides/ipu3-ipa-design-guide.rst
>>>> new file mode 100644
>>>> index 000000000000..a1d0f13fbb00
>>>> --- /dev/null
>>>> +++ b/Documentation/guides/ipu3-ipa-design-guide.rst
>>>> @@ -0,0 +1,144 @@
>>>> +IPU3 IPA Architecture Design and Overview
>>>> +=========================================
>>>> +
>>>> +The IPU3 IPA is built as a modular and extensible framework with an
>>>> +upper layer to manage the interactions with the pipeline handler, and
>>>> +the image processing algorithms split to compartmentalise the processing
>>>> +required for each accellerator cluster provided by the ImgU ISP.
>>>
>>> I've commented on the expression "accelerator cluster" when reviewing
>>> Jean-Michel's series. I've then seen that it's mentioned in the IPU3
>>> kernel documentation in one place, I suppose that's where it comes from.
>>> From what I understand, the expression is used to refer to a processing
>>> block (or sub-block) that is fully implemented in hardware, as opposed
>>> as being implemented partly or fully in the ImgU firmware. I don't think
>>> that's relevant from an IPA point of view, it's an internal
>>> implementation detail of the ImgU. I'd thus use "processing block" or a
>>> similar term instead.
>>
>> https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/drivers/staging/media/ipu3/include/uapi/intel-ipu3.h#n2428
>>
>> Describes it as:
>>
>> """
>> ACC refers to the HW cluster containing all Fixed Functions (FFs). Each
>> FF implements a specific algorithm.
>> """
>>
>> So in fact, yes - the term Accelerator Cluster is a 'group' of all the
>> hardware accelerator functions, rather than each individual one.
>>
>> Each individual function (fixed function) can indeed be better named as
>> a processing block.
>>
>>
>> Lets make this more like
>>
>> """
>> The IPU3 IPA is built as a modular and extensible framework with an
>> upper layer to manage the interactions with the pipeline handler, and
>> the image processing algorithms split to compartmentalise the processing
>> required for each processing block, making use of the fixed-function
>> accelerators provided by the ImgU ISP.
>> """
> 
> Sounds good to me. Let's standardize on the same "processing block"
> terminology in the IPU3 IPA documentation series too.

Ok,

+Cc: Jean Michel to highlight this discussion point.

> 
>>>> +
>>>> +The core IPU3 class is responsible for initialisation and construction
>>>> +of the algorithm components, processing controls set by the requests
>>>> +from applications, and managing events from the Pipeline handler.
>>>
>>> s/Pipeline/pipeline/
>>>
>>>> +
>>>> +::
>>>> +
>>>> +        ┌───────────────────────────────────────────┐
>>>> +        │      IPU3 Pipeline Handler                │
>>>> +        │   ┌────────┐    ┌────────┐    ┌────────┐  │
>>>> +        │   │        │    │        │    │        │  │
>>>> +        │   │ Sensor ├───►│  CIO2  ├───►│  ImgU  ├──►
>>>> +        │   │        │    │        │    │        │  │
>>>> +        │   └────────┘    └────────┘    └─▲────┬─┘  │    P: Parameter Buffer
>>>> +        │                                 │P   │    │    S: Statistics Buffer
>>>> +        │                                 │    │S   │
>>>> +        └─┬───┬───┬──────┬────┬────┬────┬─┴────▼─┬──┘    1: init()
>>>> +          │   │   │      │ ▲  │ ▲  │ ▲  │ ▲      │       2: configure()
>>>> +          │1  │2  │3     │4│  │4│  │4│  │4│      │5      3: mapBuffers(), start()
>>>> +          ▼   ▼   ▼      ▼ │  ▼ │  ▼ │  ▼ │      ▼       4: processEvent()
>>>> +        ┌──────────────────┴────┴────┴────┴─────────┐    5: stop(), unmapBuffers()
>>>> +        │ IPU3 IPA                                  │
>>>> +        │                 ┌───────────────────────┐ │
>>>> +        │ ┌───────────┐   │ Algorithms            │ │
>>>> +        │ │IPAContext │   │          ┌─────────┐  │ │
>>>> +        │ │ ┌───────┐ │   │          │ ...     │  │ │
>>>> +        │ │ │       │ │   │        ┌─┴───────┐ │  │ │
>>>> +        │ │ │  SC   │ │   │        │ Tonemap ├─┘  │ │
>>>> +        │ │ │       │ ◄───►      ┌─┴───────┐ │    │ │
>>>> +        │ │ ├───────┤ │   │      │ AWB     ├─┘    │ │
>>>> +        │ │ │       │ │   │    ┌─┴───────┐ │      │ │
>>>> +        │ │ │  FC   │ │   │    │ AGC     ├─┘      │ │
>>>> +        │ │ │       │ │   │    │         │        │ │
>>>> +        │ │ └───────┘ │   │    └─────────┘        │ │
>>>> +        │ └───────────┘   └───────────────────────┘ │
>>>> +        └───────────────────────────────────────────┘
>>>> +         SC: IPASessionConfiguration
>>>> +         FC: IPAFrameContext(s)
>>>> +
>>>> +The IPA instance is constructed and initialised at the point a Camera is
>>>> +created by the IPU3 pipeline handler. The initialisation call provides
>>
>> "Camera" is capitalised as a libcamera noun. Shouldn't Pipeline Handler
>> also be capitalised as it's a libcamera named thing?
>>
>> (From your comment above about s/Pipeline/pipeline/. I wonder if instead
>> it should be capitalised there and here too.
> 
> In Doxygen capitalization generates links to classes, so we have to be
> careful about writing "Camera" for instance. When it comes to pipeline
> handlers, "Pipeline Handler" won't generate a link, and I wouldn't write
> "PipelineHandler" here anyway.
> 
> I'm sure there are conventions for all this in documentation. I usually
> capitalize words that have special meanings the first time they're
> introduced only, but I don't know if that's a good thing to do.
> 
>>>> +details about which Camera Sensor is being used, and the controls that
>>>
>>> s/Camera Sensor/camera sensor/ ?
>>
>> Now that one is awkward, as it's both a libcamera noun, and a real world
>> object.
>>
>> In this context, I believe camera sensor is correct, (as you've
>> suggested) as it's the external world camera sensor details.
>>
>>>> +it has available, along with their defaults and ranges.
>>>
>>> s/defaults/default values/
>>>
>>>> +
>>>> +Buffers
>>>> +~~~~~~~
>>>> +
>>>> +The IPA will have Parameter and Statistics buffers shared with it from
>>>> +the IPU3 Pipeline handler. These buffers will be passed to the IPA
>>>> +before the ``start()`` operation occurs.
>>>> +
>>>> +The IPA will map the buffers into CPU accessible memory, associated with
>>>
>>> s/CPU accessible/CPU-accessible/
>>>
>>>> +a buffer ID, and further events for sending or receiving parameter and
>>>> +statistics buffers will reference the ID to avoid expensive memory
>>>> +mapping operations, or the passing of file handles during streaming.
>>>> +
>>>> +After the ``stop()`` operation occurs, these buffers will be unmapped,
>>>> +and no further access to the buffers is permitted.
>>>> +
>>>> +Context
>>>> +~~~~~~~
>>>> +
>>>> +Algorithm calls will always have the ``IPAContext`` available to them.
>>>> +This context comprises of two parts:
>>>> +
>>>> +-  IPA Session Configuration
>>>> +-  IPA Frame Context
>>>> +
>>>> +The session configuration structure ``IPASessionConfiguration``
>>>> +represents constant parameters determined from either before streaming
>>>> +commenced during ``configure()`` or updated parameters when processing
>>>> +controls.
>>>
>>> I'm not sure about the last part, I thought the session configuration
>>> was meant to be constant after configure() ?
>>
>> I would expect updates from controls to update the 'active session
>> configuration'.
>>
>> Of course some of that session configuration will be constant, and not
>> change (I don't think we'll change the resolution for instance) - but I
>> expect that some parameters will be set such as whether AE is enabled or
>> locked.
>>
>> That to me is a session configuration parameter. But it can change at
>> runtime - and while it remains the same, every new frame will have that
>> configuration applied.
>>
>>
>> Whereas the FrameContexts are about the context that is handled for each
>> frame, and any context shared between algorithms , and is much more dynamic.
> 
> This makes me think that we may want to introduce a third structure to
> group state that isn't per-frame. I recall designing
> IPASessionConfiguration as something that will not change during the
> session. Maybe I recall it wrong, but I like the idea of keeping it

But ... state that isn't per frame is the ... session ? and thus that
state is stored as the SessionConfiguration ...

At the moment I anticipate we'll need to store things like control
state. I.e. is AE enabled or manual for instance. And if manual - what
is the current fixed manual value.

I expected that would be the session configuration, as in it's the
current active settings ... but maybe a third group would come up, I
think we'll find out when we actually add the controls.


> static. Separating configuration that is set at the beginning and
> doesn't change from controls that are updated dynamically seems a good
> design principle to me.


I'll delete the last part:
"or updated parameters when processing controls."


We can revisit this when we add controls.



>>>> +The IPA Frame Context provides the storage for algorithms for a single
>>>> +frame operation.
>>>> +
>>>> +The ``IPAFrameContext`` structure may be extended to an array, list, or
>>>> +queue to store historical state for each frame, allowing algorithms to
>>>> +obtain and reference results of calculations which are deeply pipelined.
>>>> +This may only be done if an algorithm needs to know the context that was
>>>> +applied at the frame the statistics were produced for, rather than the
>>>> +previous or current frame.
>>>> +
>>>> +Presently there is a single ``IPAFrameContext`` without historical data,
>>>> +and the context is maintained and updated through successive processing
>>>> +operations.
>>>> +
>>>> +Operating
>>>> +~~~~~~~~~
>>>> +
>>>> +There are three main parts of interactions with the algorithms for the
>>>> +IPU3 IPA to operate when running:
>>>> +
>>>> +-  configure()
>>>> +-  processEvent(``EventFillParams``)
>>>> +-  processEvent(``EventStatReady``)
>>>> +
>>>> +The configuration phase allows the pipeline-handler to inform the IPA of
>>>> +the current stream configurations, which is then passed into each
>>>> +algorithm to provide an opportunity to identify and track state of the
>>>> +hardware, such as image size or ImgU pipeline configurations.
>>>> +
>>>> +Pre-frame preparation
>>>> +~~~~~~~~~~~~~~~~~~~~~
>>>> +
>>>> +When configured, the IPA is notified by the pipeline handler of the
>>>> +Camera ``start()`` event, after which incoming requests will be queued
>>>> +for processing, requiring a parameter buffer (``ipu3_uapi_params``) to
>>>> +be populated for the ImgU. This is passed directly to each algorithm
>>>> +through the ``prepare()`` call allowing the ISP configuration to be
>>>> +updated for the needs of each component that the algorithm is
>>>> +responsible for.
>>>> +
>>>> +The algorithm should set the use flag (``ipu3_uapi_flags``) for any
>>>> +structure that it modifies, and it should take care to ensure that any
>>>> +structure set by a use flag is fully initialised to suitable values.
>>>> +
>>>> +The parameter buffer is returned to the pipeline handler through the
>>>> +``ActionParamFilled`` event, and from there queued to the ImgU along
>>>> +with a raw frame captured with the CIO2.
>>>
>>> This reminds me that we should turn the operations (actions and events)
>>> into separate functions in the IPAIPU3Interface. Out of scope for this
>>> patch of course.
>>
>> You mean directly defining them in Mojo instead of passing them through
>> processEvent with an event flag?
> 
> Yes.

That sounds like a good thing to do, and may indeed make the interfaces
clearer I think.

We may have to further document the expectations of those calls for both
directions. I.e. EventFillParams (or it's new direct call equivalent) is
expected to call or initiate the calling of a return of the buffer
through ActionParamFilled (or it's renamed direct call equivalent).



>> I think that would probably be better indeed, I don't see much added
>> value to having processEvent() ... (with the small exception that it
>> partially shows which functions are called while streaming, but we could
>> also document the async/streaming expectations anyway).
> 
> processEvent() dates back from when we tried to have a single generic
> API for IPAs.

And we clearly have per - pipeline handler IPA's now.


>>>> +
>>>> +Post-frame completion
>>>> +~~~~~~~~~~~~~~~~~~~~~
>>>> +
>>>> +When the capture of an image is completed, and successfully processed
>>>> +through the ImgU, the generated statistics buffer
>>>> +(``ipu3_uapi_stats_3a``) is given to the IPA through the
>>>> +``EventStatReady`` event. This provides the IPA with an opportunity to
>>>> +examine the results of the ISP and run the calculations required by each
>>>> +algorithm on the new data. The algorithms may require context from the
>>>> +operations of other algorithms, for example, the AWB might choose to use
>>>> +a scene brightness determined by the AGC. It is important that the
>>>> +algorithms are ordered to ensure that required results are determined
>>>> +before they are needed.
>>>> +
>>>> +The ordering of the algorithm processing is determined by their
>>>> +placement in the ``IPU3::algorithms_`` ordered list.
>>>
>>> I expect interesting research to happen in this area :-)
>>
>> Yes, well it's too early to state any more than that currently I think.
> 


More information about the libcamera-devel mailing list