[libcamera-devel] [PATCH v6 1/1] Fix Android adaptor thumbnail buffer lifetime
Cheng-Hao Yang
chenghaoyang at chromium.org
Fri Jul 22 09:07:15 CEST 2022
Thanks Umang & Laurent!
Followed most of your suggestions and sent the PATCH v2. Please check :)
BR,
Harvey
On Fri, Jul 22, 2022 at 3:30 AM Laurent Pinchart <
laurent.pinchart at ideasonboard.com> wrote:
> Hello,
>
> On Thu, Jul 21, 2022 at 11:14:16PM +0530, Umang Jain via libcamera-devel
> wrote:
> > On 7/20/22 15:28, Harvey Yang via libcamera-devel wrote:
> > > Previously the thumbnail buffer is destructed before even being used in
> >
> > Great catch, I think this was the reason for flaky failure for
> > Camera3SimpleStillCaptureTest.JpegExifTest as mentioned!
>
> Oh indeed ! Nice !
>
> > > Exif. This patch moves the buffer into class Exif, so that the
> developer
> > > won't need to worry about its lifetime.
> > >
> > > Signed-off-by: Harvey Yang <chenghaoyang at chromium.org>
> > > ---
> > > src/android/jpeg/exif.cpp | 10 ++++++----
> > > src/android/jpeg/exif.h | 10 ++++++++--
> > > src/android/jpeg/post_processor_jpeg.cpp | 6 ++----
> > > 3 files changed, 16 insertions(+), 10 deletions(-)
> > >
> > > diff --git a/src/android/jpeg/exif.cpp b/src/android/jpeg/exif.cpp
> > > index 3220b458..584a29d0 100644
> > > --- a/src/android/jpeg/exif.cpp
> > > +++ b/src/android/jpeg/exif.cpp
> > > @@ -435,11 +435,13 @@ void Exif::setOrientation(int orientation)
> > > * Failing to do so, might result in no thumbnail data being set
> even after a
> > > * call to Exif::setThumbnail().
> > > */
>
> Note that the issue is documented here. Clearly that wasn't enough, so
> the API isn't good and needs to be changed. The comment can thus be
> dropped.
>
> > > -void Exif::setThumbnail(Span<const unsigned char> thumbnail,
> > > - Compression compression)
> > > +void Exif::setThumbnail(Compression compression)
> > > {
> > > - data_->data = const_cast<unsigned char *>(thumbnail.data());
> > > - data_->size = thumbnail.size();
> > > + if (thumbnail_raw_.empty())
> > > + return;
> > > +
> > > + data_->data = const_cast<unsigned char *>(thumbnail_raw_.data());
> >
> > I think we can do away with the const_cast here? Might not be compatible
> > with previous C++ versions?
> >
> > I quickly compile tested
> >
> > - data_->data = const_cast<unsigned char *>(thumbnail_raw_.data());
> > + data_->data = thumbnail_raw_.data();
> >
> > on clang version 12.0.1 and gcc (GCC) 11.0.1 which seems OK.
>
> There should be no need for a const_cast, indeed.
>
> > > + data_->size = thumbnail_raw_.size();
>
> I would do this a bit differently, to avoid the getThumbnailRaw(), which
> really creates an interdependency between the Exif class and the
> PostProcessorJpeg class.
>
> void Exif::setThumbnail(std::vector<uint8_t> &&data, Compression
> compression)
> {
> thumbnail_raw_ = std::move(data);
>
> data_->data = thumbnail_raw_.data();
> data_->size = thumbnail_raw_.size();
>
> setShort(EXIF_IFD_0, EXIF_TAG_COMPRESSION, compression);
> }
>
> The only change to the caller compared to the current code would then be
>
> - exif.setThumbnail(thumbnail,
> Exif::Compression::JPEG);
> + exif.setThumbnail(std::move(thumbnail),
> + Exif::Compression::JPEG);
>
> > >
> > > setShort(EXIF_IFD_0, EXIF_TAG_COMPRESSION, compression);
> > > }
> > > diff --git a/src/android/jpeg/exif.h b/src/android/jpeg/exif.h
> > > index 2ff8fb78..4784496b 100644
> > > --- a/src/android/jpeg/exif.h
> > > +++ b/src/android/jpeg/exif.h
> > > @@ -10,6 +10,7 @@
> > > #include <chrono>
> > > #include <string>
> > > #include <time.h>
> > > +#include <vector>
> > >
> > > #include <libexif/exif-data.h>
> > >
> > > @@ -60,8 +61,7 @@ public:
> > >
> > > void setOrientation(int orientation);
> > > void setSize(const libcamera::Size &size);
> > > - void setThumbnail(libcamera::Span<const unsigned char> thumbnail,
> > > - Compression compression);
> > > + void setThumbnail(Compression compression);
> > > void setTimestamp(time_t timestamp, std::chrono::milliseconds
> msec);
> > >
> > > void setGPSDateTimestamp(time_t timestamp);
> > > @@ -78,6 +78,10 @@ public:
> > > libcamera::Span<const uint8_t> data() const { return { exifData_,
> size_ }; }
> > > [[nodiscard]] int generate();
> > >
> > > + std::vector<unsigned char>& getThumbnailRaw() {
> > > + return thumbnail_raw_;
> > > + }
> > > +
> > > private:
> > > ExifEntry *createEntry(ExifIfd ifd, ExifTag tag);
> > > ExifEntry *createEntry(ExifIfd ifd, ExifTag tag, ExifFormat format,
> > > @@ -106,4 +110,6 @@ private:
> > >
> > > unsigned char *exifData_;
> > > unsigned int size_;
> > > +
> > > + std::vector<unsigned char> thumbnail_raw_;
> >
> > CamelCase everywhere please ;-)
>
> And I'd call it thumbnailData_, or just thumbnail_.
>
> > Once reviewed by someone else, I 'll handle the merge so,
> >
> > Reviewed-by: Umang Jain <umang.jain at ideasonboard.com>
> >
> > > };
> > > diff --git a/src/android/jpeg/post_processor_jpeg.cpp
> b/src/android/jpeg/post_processor_jpeg.cpp
> > > index d72ebc3c..506b00b9 100644
> > > --- a/src/android/jpeg/post_processor_jpeg.cpp
> > > +++ b/src/android/jpeg/post_processor_jpeg.cpp
> > > @@ -163,10 +163,8 @@ void
> PostProcessorJpeg::process(Camera3RequestDescriptor::StreamBuffer *streamBu
> > > resultMetadata->addEntry(ANDROID_JPEG_THUMBNAIL_QUALITY,
> quality);
> > >
> > > if (thumbnailSize != Size(0, 0)) {
> > > - std::vector<unsigned char> thumbnail;
> > > - generateThumbnail(source, thumbnailSize, quality,
> &thumbnail);
> > > - if (!thumbnail.empty())
> > > - exif.setThumbnail(thumbnail,
> Exif::Compression::JPEG);
> > > + generateThumbnail(source, thumbnailSize, quality,
> &exif.getThumbnailRaw());
> > > + exif.setThumbnail(Exif::Compression::JPEG);
> > > }
> > >
> > > resultMetadata->addEntry(ANDROID_JPEG_THUMBNAIL_SIZE,
> data, 2);
>
> --
> Regards,
>
> Laurent Pinchart
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.libcamera.org/pipermail/libcamera-devel/attachments/20220722/b9cb4862/attachment.htm>
More information about the libcamera-devel
mailing list