// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "media/gpu/vaapi/vaapi_mjpeg_decode_accelerator.h"

#include <stddef.h>
#include <sys/mman.h>
#include <va/va.h>

#include <array>
#include <utility>

#include "base/bind.h"
#include "base/callback_helpers.h"
#include "base/files/scoped_file.h"
#include "base/location.h"
#include "base/logging.h"
#include "base/memory/page_size.h"
#include "base/metrics/histogram_macros.h"
#include "base/numerics/checked_math.h"
#include "base/numerics/safe_conversions.h"
#include "base/single_thread_task_runner.h"
#include "base/threading/thread_task_runner_handle.h"
#include "base/trace_event/trace_event.h"
#include "gpu/ipc/common/gpu_memory_buffer_impl.h"
#include "media/base/bind_to_current_loop.h"
#include "media/base/bitstream_buffer.h"
#include "media/base/format_utils.h"
#include "media/base/unaligned_shared_memory.h"
#include "media/base/video_frame.h"
#include "media/base/video_frame_layout.h"
#include "media/base/video_util.h"
#include "media/gpu/chromeos/fourcc.h"
#include "media/gpu/chromeos/libyuv_image_processor_backend.h"
#include "media/gpu/chromeos/platform_video_frame_utils.h"
#include "media/gpu/macros.h"
#include "media/gpu/vaapi/va_surface.h"
#include "media/gpu/vaapi/vaapi_image_decoder.h"
#include "media/gpu/vaapi/vaapi_utils.h"
#include "media/gpu/vaapi/vaapi_wrapper.h"
#include "third_party/abseil-cpp/absl/types/optional.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/gfx/geometry/size.h"
#include "ui/gfx/gpu_memory_buffer.h"

namespace media {

namespace {

void ReportToVAJDAResponseToClientUMA(
    chromeos_camera::MjpegDecodeAccelerator::Error response) {
  UMA_HISTOGRAM_ENUMERATION(
      "Media.VAJDA.ResponseToClient", response,
      chromeos_camera::MjpegDecodeAccelerator::Error::MJDA_ERROR_CODE_MAX + 1);
}

chromeos_camera::MjpegDecodeAccelerator::Error VaapiJpegDecodeStatusToError(
    VaapiImageDecodeStatus status) {
  switch (status) {
    case VaapiImageDecodeStatus::kSuccess:
      return chromeos_camera::MjpegDecodeAccelerator::Error::NO_ERRORS;
    case VaapiImageDecodeStatus::kParseFailed:
      return chromeos_camera::MjpegDecodeAccelerator::Error::PARSE_JPEG_FAILED;
    case VaapiImageDecodeStatus::kUnsupportedSubsampling:
      return chromeos_camera::MjpegDecodeAccelerator::Error::UNSUPPORTED_JPEG;
    default:
      return chromeos_camera::MjpegDecodeAccelerator::Error::PLATFORM_FAILURE;
  }
}

bool VerifyDataSize(const VAImage* image) {
  const gfx::Size dimensions(base::strict_cast<int>(image->width),
                             base::strict_cast<int>(image->height));
  size_t min_size = 0;
  if (image->format.fourcc == VA_FOURCC_I420) {
    min_size = VideoFrame::AllocationSize(PIXEL_FORMAT_I420, dimensions);
  } else if (image->format.fourcc == VA_FOURCC_NV12) {
    min_size = VideoFrame::AllocationSize(PIXEL_FORMAT_NV12, dimensions);
  } else if (image->format.fourcc == VA_FOURCC_YUY2 ||
             image->format.fourcc == VA_FOURCC('Y', 'U', 'Y', 'V')) {
    min_size = VideoFrame::AllocationSize(PIXEL_FORMAT_YUY2, dimensions);
  } else {
    return false;
  }
  return base::strict_cast<size_t>(image->data_size) >= min_size;
}

}  // namespace

void VaapiMjpegDecodeAccelerator::NotifyError(int32_t task_id, Error error) {
  if (!task_runner_->BelongsToCurrentThread()) {
    task_runner_->PostTask(
        FROM_HERE,
        base::BindOnce(&VaapiMjpegDecodeAccelerator::NotifyError,
                       weak_this_factory_.GetWeakPtr(), task_id, error));
    return;
  }
  VLOGF(1) << "Notifying of error " << error;
  // |error| shouldn't be NO_ERRORS because successful decodes should be handled
  // by VideoFrameReady().
  DCHECK_NE(chromeos_camera::MjpegDecodeAccelerator::Error::NO_ERRORS, error);
  ReportToVAJDAResponseToClientUMA(error);
  DCHECK(client_);
  client_->NotifyError(task_id, error);
}

void VaapiMjpegDecodeAccelerator::VideoFrameReady(int32_t task_id) {
  DCHECK(task_runner_->BelongsToCurrentThread());
  ReportToVAJDAResponseToClientUMA(
      chromeos_camera::MjpegDecodeAccelerator::Error::NO_ERRORS);
  client_->VideoFrameReady(task_id);
}

VaapiMjpegDecodeAccelerator::VaapiMjpegDecodeAccelerator(
    const scoped_refptr<base::SingleThreadTaskRunner>& io_task_runner)
    : task_runner_(base::ThreadTaskRunnerHandle::Get()),
      io_task_runner_(io_task_runner),
      client_(nullptr),
      decoder_thread_("VaapiMjpegDecoderThread"),
      weak_this_factory_(this) {}

// Some members expect to be destroyed on the |decoder_thread_|.
void VaapiMjpegDecodeAccelerator::CleanUpOnDecoderThread() {
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());
  DCHECK(vpp_vaapi_wrapper_->HasOneRef());
  vpp_vaapi_wrapper_.reset();
  decoder_.reset();
  image_processor_.reset();
}

VaapiMjpegDecodeAccelerator::~VaapiMjpegDecodeAccelerator() {
  DCHECK(task_runner_->BelongsToCurrentThread());
  VLOGF(2) << "Destroying VaapiMjpegDecodeAccelerator";
  weak_this_factory_.InvalidateWeakPtrs();

  if (decoder_task_runner_) {
    // base::Unretained() is fine here because we control |decoder_task_runner_|
    // lifetime.
    decoder_task_runner_->PostTask(
        FROM_HERE,
        base::BindOnce(&VaapiMjpegDecodeAccelerator::CleanUpOnDecoderThread,
                       base::Unretained(this)));
  }
  decoder_thread_.Stop();
}

void VaapiMjpegDecodeAccelerator::InitializeOnDecoderTaskRunner(
    chromeos_camera::MjpegDecodeAccelerator::InitCB init_cb) {
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());

  decoder_ = std::make_unique<media::VaapiJpegDecoder>();
  if (!decoder_->Initialize(base::BindRepeating(
          &ReportVaapiErrorToUMA,
          "Media.VaapiMjpegDecodeAccelerator.VAAPIError"))) {
    VLOGF(1) << "Failed initializing |decoder_|";
    std::move(init_cb).Run(false);
    return;
  }

  vpp_vaapi_wrapper_ = VaapiWrapper::Create(
      VaapiWrapper::kVideoProcess, VAProfileNone,
      EncryptionScheme::kUnencrypted,
      base::BindRepeating(&ReportVaapiErrorToUMA,
                          "Media.VaapiMjpegDecodeAccelerator.Vpp.VAAPIError"));
  if (!vpp_vaapi_wrapper_) {
    VLOGF(1) << "Failed initializing VAAPI for VPP";
    std::move(init_cb).Run(false);
    return;
  }

  // Size is irrelevant for a VPP context.
  if (!vpp_vaapi_wrapper_->CreateContext(gfx::Size())) {
    VLOGF(1) << "Failed to create context for VPP";
    std::move(init_cb).Run(false);
    return;
  }

  std::move(init_cb).Run(true);
}

void VaapiMjpegDecodeAccelerator::InitializeOnTaskRunner(
    chromeos_camera::MjpegDecodeAccelerator::Client* client,
    chromeos_camera::MjpegDecodeAccelerator::InitCB init_cb) {
  DCHECK(task_runner_->BelongsToCurrentThread());
  client_ = client;

  if (!decoder_thread_.Start()) {
    VLOGF(1) << "Failed to start decoding thread.";
    std::move(init_cb).Run(false);
    return;
  }
  decoder_task_runner_ = decoder_thread_.task_runner();

  // base::Unretained() is fine here because we control |decoder_task_runner_|
  // lifetime.
  decoder_task_runner_->PostTask(
      FROM_HERE,
      base::BindOnce(
          &VaapiMjpegDecodeAccelerator::InitializeOnDecoderTaskRunner,
          base::Unretained(this), std::move(init_cb)));
}

void VaapiMjpegDecodeAccelerator::InitializeAsync(
    chromeos_camera::MjpegDecodeAccelerator::Client* client,
    chromeos_camera::MjpegDecodeAccelerator::InitCB init_cb) {
  VLOGF(2);
  DCHECK(task_runner_->BelongsToCurrentThread());

  // To guarantee that the caller receives an asynchronous call after the
  // return path, we are making use of InitializeOnTaskRunner.
  task_runner_->PostTask(
      FROM_HERE,
      base::BindOnce(&VaapiMjpegDecodeAccelerator::InitializeOnTaskRunner,
                     weak_this_factory_.GetWeakPtr(), client,
                     BindToCurrentLoop(std::move(init_cb))));
}

void VaapiMjpegDecodeAccelerator::CreateImageProcessor(
    const VideoFrame* src_frame,
    const VideoFrame* dst_frame) {
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());

  // The fourcc of |src_frame| will be either Fourcc(YUYV) or Fourcc(YU12) based
  // on the implementation of OutputPictureLibYuvOnTaskRunner(). The fourcc of
  // |dst_frame| should have been validated in DecodeImpl().
  const auto src_fourcc = Fourcc::FromVideoPixelFormat(src_frame->format());
  DCHECK(src_fourcc.has_value());
  const auto dst_fourcc = Fourcc::FromVideoPixelFormat(dst_frame->format());
  DCHECK(dst_fourcc.has_value());
  const ImageProcessorBackend::PortConfig input_config(
      *src_fourcc, src_frame->coded_size(), src_frame->layout().planes(),
      src_frame->visible_rect(), {src_frame->storage_type()});
  const ImageProcessorBackend::PortConfig output_config(
      *dst_fourcc, dst_frame->coded_size(), dst_frame->layout().planes(),
      dst_frame->visible_rect(), {dst_frame->storage_type()});
  if (image_processor_ && image_processor_->input_config() == input_config &&
      image_processor_->output_config() == output_config) {
    return;
  }

  // The error callback is posted to the same thread that
  // LibYUVImageProcessorBackend::Create() is called on
  // (i.e., |decoder_thread_|) and we control the lifetime of |decoder_thread_|.
  // Therefore, base::Unretained(this) is safe.
  image_processor_ = LibYUVImageProcessorBackend::Create(
      input_config, output_config, {ImageProcessorBackend::OutputMode::IMPORT},
      VIDEO_ROTATION_0,
      base::BindRepeating(&VaapiMjpegDecodeAccelerator::OnImageProcessorError,
                          base::Unretained(this)),
      decoder_task_runner_);
}

bool VaapiMjpegDecodeAccelerator::OutputPictureLibYuvOnTaskRunner(
    int32_t task_id,
    std::unique_ptr<ScopedVAImage> scoped_image,
    scoped_refptr<VideoFrame> video_frame,
    const gfx::Rect& crop_rect) {
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());

  TRACE_EVENT1("jpeg", __func__, "task_id", task_id);

  DCHECK(scoped_image);
  const VAImage* image = scoped_image->image();
  DCHECK(VerifyDataSize(image));
  const gfx::Size src_size(base::strict_cast<int>(image->width),
                           base::strict_cast<int>(image->height));
  DCHECK(gfx::Rect(src_size).Contains(crop_rect));

  // Wrap |image| into VideoFrame.
  std::vector<int32_t> strides(image->num_planes);
  for (uint32_t i = 0; i < image->num_planes; ++i) {
    if (!base::CheckedNumeric<uint32_t>(image->pitches[i])
             .AssignIfValid(&strides[i])) {
      VLOGF(1) << "Invalid VAImage stride " << image->pitches[i]
               << " for plane " << i;
      return false;
    }
  }
  auto* const data = static_cast<uint8_t*>(scoped_image->va_buffer()->data());
  scoped_refptr<VideoFrame> src_frame;
  switch (image->format.fourcc) {
    case VA_FOURCC_YUY2:
    case VA_FOURCC('Y', 'U', 'Y', 'V'): {
      auto layout = VideoFrameLayout::CreateWithStrides(PIXEL_FORMAT_YUY2,
                                                        src_size, strides);
      if (!layout.has_value()) {
        VLOGF(1) << "Failed to create video frame layout";
        return false;
      }
      src_frame = VideoFrame::WrapExternalDataWithLayout(
          *layout, crop_rect, crop_rect.size(), data + image->offsets[0],
          base::strict_cast<size_t>(image->data_size), base::TimeDelta());
      break;
    }
    case VA_FOURCC_I420: {
      auto layout = VideoFrameLayout::CreateWithStrides(PIXEL_FORMAT_I420,
                                                        src_size, strides);
      if (!layout.has_value()) {
        VLOGF(1) << "Failed to create video frame layout";
        return false;
      }
      src_frame = VideoFrame::WrapExternalYuvDataWithLayout(
          *layout, crop_rect, crop_rect.size(), data + image->offsets[0],
          data + image->offsets[1], data + image->offsets[2],
          base::TimeDelta());
      break;
    }
    default:
      VLOGF(1) << "Unsupported VA image format: "
               << FourccToString(image->format.fourcc);
      return false;
  }
  if (!src_frame) {
    VLOGF(1) << "Failed to create video frame";
    return false;
  }

  CreateImageProcessor(src_frame.get(), video_frame.get());
  if (!image_processor_) {
    VLOGF(1) << "Failed to create image processor";
    return false;
  }
  image_processor_->Process(
      std::move(src_frame), std::move(video_frame),
      base::BindOnce(
          [](scoped_refptr<base::SingleThreadTaskRunner> runner,
             base::OnceClosure cb, scoped_refptr<VideoFrame> frame) {
            runner->PostTask(FROM_HERE, std::move(cb));
          },
          task_runner_,
          base::BindOnce(&VaapiMjpegDecodeAccelerator::VideoFrameReady,
                         weak_this_factory_.GetWeakPtr(), task_id)));
  return true;
}

void VaapiMjpegDecodeAccelerator::OnImageProcessorError() {
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());
  VLOGF(1) << "Failed to process frames using the libyuv image processor";
  NotifyError(kInvalidTaskId, PLATFORM_FAILURE);
  image_processor_.reset();
}

bool VaapiMjpegDecodeAccelerator::OutputPictureVppOnTaskRunner(
    int32_t task_id,
    const ScopedVASurface* surface,
    scoped_refptr<VideoFrame> video_frame,
    const gfx::Rect& crop_rect) {
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());
  DCHECK(surface);
  DCHECK(video_frame);
  DCHECK(gfx::Rect(surface->size()).Contains(crop_rect));

  TRACE_EVENT1("jpeg", __func__, "task_id", task_id);

  scoped_refptr<gfx::NativePixmap> pixmap =
      CreateNativePixmapDmaBuf(video_frame.get());
  if (!pixmap) {
    VLOGF(1) << "Failed to create NativePixmap from VideoFrame";
    return false;
  }

  // Bind a VA surface to |video_frame|.
  scoped_refptr<VASurface> output_surface =
      vpp_vaapi_wrapper_->CreateVASurfaceForPixmap(std::move(pixmap));
  if (!output_surface) {
    VLOGF(1) << "Cannot create VA surface for output buffer";
    return false;
  }

  scoped_refptr<VASurface> src_surface = base::MakeRefCounted<VASurface>(
      surface->id(), surface->size(), surface->format(),
      /*release_cb=*/base::DoNothing());

  // We should call vaSyncSurface() when passing surface between contexts. See:
  // https://lists.01.org/pipermail/intel-vaapi-media/2019-June/000131.html
  if (!vpp_vaapi_wrapper_->SyncSurface(surface->id())) {
    VLOGF(1) << "Cannot sync VPP input surface";
    return false;
  }
  if (!vpp_vaapi_wrapper_->BlitSurface(*src_surface, *output_surface,
                                       crop_rect)) {
    VLOGF(1) << "Cannot convert decoded image into output buffer";
    return false;
  }

  // Sync target surface since the buffer is returning to client.
  if (!vpp_vaapi_wrapper_->SyncSurface(output_surface->id())) {
    VLOGF(1) << "Cannot sync VPP output surface";
    return false;
  }

  task_runner_->PostTask(
      FROM_HERE, base::BindOnce(&VaapiMjpegDecodeAccelerator::VideoFrameReady,
                                weak_this_factory_.GetWeakPtr(), task_id));

  return true;
}

void VaapiMjpegDecodeAccelerator::DecodeFromShmTask(
    int32_t task_id,
    std::unique_ptr<UnalignedSharedMemory> shm,
    scoped_refptr<VideoFrame> dst_frame) {
  DVLOGF(4);
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());
  TRACE_EVENT0("jpeg", __func__);

  auto src_image =
      base::make_span(static_cast<const uint8_t*>(shm->memory()), shm->size());
  DecodeImpl(task_id, src_image, std::move(dst_frame));
}

void VaapiMjpegDecodeAccelerator::DecodeFromDmaBufTask(
    int32_t task_id,
    base::ScopedFD src_dmabuf_fd,
    size_t src_size,
    off_t src_offset,
    scoped_refptr<VideoFrame> dst_frame) {
  DVLOGF(4);
  DCHECK(decoder_task_runner_->BelongsToCurrentThread());
  TRACE_EVENT0("jpeg", __func__);

  // The DMA-buf FD should be mapped as read-only since it may only have read
  // permission, e.g. when it comes from camera driver.
  DCHECK(src_dmabuf_fd.is_valid());
  DCHECK_GT(src_size, 0u);
  void* src_addr = mmap(nullptr, src_size, PROT_READ, MAP_SHARED,
                        src_dmabuf_fd.get(), src_offset);
  if (src_addr == MAP_FAILED) {
    VPLOGF(1) << "Failed to map input DMA buffer";
    NotifyError(task_id, UNREADABLE_INPUT);
    return;
  }
  base::span<const uint8_t> src_image =
      base::make_span(static_cast<const uint8_t*>(src_addr), src_size);

  DecodeImpl(task_id, src_image, std::move(dst_frame));

  const int ret = munmap(src_addr, src_size);
  DPCHECK(ret == 0);
}

void VaapiMjpegDecodeAccelerator::DecodeImpl(
    int32_t task_id,
    base::span<const uint8_t> src_image,
    scoped_refptr<VideoFrame> dst_frame) {
  VaapiImageDecodeStatus status = decoder_->Decode(src_image);
  if (status != VaapiImageDecodeStatus::kSuccess) {
    VLOGF(1) << "Failed to decode JPEG image";
    NotifyError(task_id, VaapiJpegDecodeStatusToError(status));
    return;
  }
  const ScopedVASurface* surface = decoder_->GetScopedVASurface();
  DCHECK(surface);
  DCHECK(surface->IsValid());

  // For camera captures, we assume that the visible size is the same as the
  // coded size.
  if (dst_frame->visible_rect().size() != dst_frame->coded_size() ||
      dst_frame->visible_rect().x() != 0 ||
      dst_frame->visible_rect().y() != 0) {
    VLOGF(1)
        << "The video frame visible size should be the same as the coded size";
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }

  // Note that |surface->size()| is the visible size of the JPEG image. The
  // underlying VASurface size (coded size) can be larger because of alignments.
  if (surface->size().width() < dst_frame->visible_rect().width() ||
      surface->size().height() < dst_frame->visible_rect().height()) {
    VLOGF(1) << "Invalid JPEG image and video frame sizes: "
             << surface->size().ToString() << ", "
             << dst_frame->visible_rect().size().ToString();
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }

  // For DMA-buf backed |dst_frame|, we will import it as a VA surface and use
  // VPP to convert the decoded |surface| into it, if the formats and sizes are
  // supported.
  const auto dst_frame_fourcc =
      Fourcc::FromVideoPixelFormat(dst_frame->format());
  if (!dst_frame_fourcc) {
    VLOGF(1) << "Unsupported video frame format: " << dst_frame->format();
    NotifyError(task_id, PLATFORM_FAILURE);
    return;
  }

  const auto dst_frame_va_fourcc = dst_frame_fourcc->ToVAFourCC();
  if (!dst_frame_va_fourcc) {
    VLOGF(1) << "Unsupported video frame format: " << dst_frame->format();
    NotifyError(task_id, PLATFORM_FAILURE);
    return;
  }

  // Crop and scale the decoded image into |dst_frame|.
  // The VPP is known to have some problems with odd-sized buffers, so we
  // request a crop rectangle whose dimensions are aligned to 2.
  const gfx::Rect crop_rect = CropSizeForScalingToTarget(
      surface->size(), dst_frame->visible_rect().size(), /*alignment=*/2u);
  if (crop_rect.IsEmpty()) {
    VLOGF(1) << "Failed to calculate crop rectangle for "
             << surface->size().ToString() << " to "
             << dst_frame->visible_rect().size().ToString();
    NotifyError(task_id, PLATFORM_FAILURE);
    return;
  }

  // TODO(kamesan): move HasDmaBufs() to DCHECK when we deprecate
  // shared-memory-backed video frame.
  // Check all the sizes involved until we figure out the definition of min/max
  // resolutions in the VPP profile (b/195312242).
  if (dst_frame->HasDmaBufs() &&
      VaapiWrapper::IsVppResolutionAllowed(surface->size()) &&
      VaapiWrapper::IsVppResolutionAllowed(crop_rect.size()) &&
      VaapiWrapper::IsVppResolutionAllowed(dst_frame->visible_rect().size()) &&
      VaapiWrapper::IsVppSupportedForJpegDecodedSurfaceToFourCC(
          surface->format(), *dst_frame_va_fourcc)) {
    if (!OutputPictureVppOnTaskRunner(task_id, surface, std::move(dst_frame),
                                      crop_rect)) {
      VLOGF(1) << "Output picture using VPP failed";
      NotifyError(task_id, PLATFORM_FAILURE);
    }
    return;
  }

  // Fallback to do conversion by libyuv. This happens when:
  // 1. |dst_frame| is backed by shared memory.
  // 2. VPP doesn't support the format conversion. This is intended for AMD
  //    VAAPI driver whose VPP only supports converting decoded 4:2:0 JPEGs.
  std::unique_ptr<ScopedVAImage> image =
      decoder_->GetImage(*dst_frame_va_fourcc, &status);
  if (status != VaapiImageDecodeStatus::kSuccess) {
    NotifyError(task_id, VaapiJpegDecodeStatusToError(status));
    return;
  }
  DCHECK_EQ(image->image()->width, surface->size().width());
  DCHECK_EQ(image->image()->height, surface->size().height());
  if (!OutputPictureLibYuvOnTaskRunner(task_id, std::move(image),
                                       std::move(dst_frame), crop_rect)) {
    VLOGF(1) << "Output picture using libyuv failed";
    NotifyError(task_id, PLATFORM_FAILURE);
  }
}

void VaapiMjpegDecodeAccelerator::Decode(
    BitstreamBuffer bitstream_buffer,
    scoped_refptr<VideoFrame> video_frame) {
  DCHECK(io_task_runner_->BelongsToCurrentThread());
  TRACE_EVENT1("jpeg", __func__, "input_id", bitstream_buffer.id());

  DVLOGF(4) << "Mapping new input buffer id: " << bitstream_buffer.id()
            << " size: " << bitstream_buffer.size();

  if (bitstream_buffer.id() < 0) {
    VLOGF(1) << "Invalid bitstream_buffer, id: " << bitstream_buffer.id();
    NotifyError(bitstream_buffer.id(), INVALID_ARGUMENT);
    return;
  }

  // Validate output video frame.
  if (!video_frame->IsMappable() && !video_frame->HasDmaBufs()) {
    VLOGF(1) << "Unsupported output frame storage type";
    NotifyError(bitstream_buffer.id(), INVALID_ARGUMENT);
    return;
  }
  if ((video_frame->visible_rect().width() & 1) ||
      (video_frame->visible_rect().height() & 1)) {
    VLOGF(1) << "Video frame visible size has odd dimension";
    NotifyError(bitstream_buffer.id(), PLATFORM_FAILURE);
    return;
  }

  // UnalignedSharedMemory will take over the |bitstream_buffer.handle()|.
  auto shm = std::make_unique<UnalignedSharedMemory>(
      bitstream_buffer.TakeRegion(), bitstream_buffer.size(),
      false /* read_only */);

  if (!shm->MapAt(bitstream_buffer.offset(), bitstream_buffer.size())) {
    VLOGF(1) << "Failed to map input buffer";
    NotifyError(bitstream_buffer.id(), UNREADABLE_INPUT);
    return;
  }

  // It's safe to use base::Unretained(this) because |decoder_task_runner_| runs
  // tasks on |decoder_thread_| which is stopped in the destructor of |this|.
  decoder_task_runner_->PostTask(
      FROM_HERE, base::BindOnce(&VaapiMjpegDecodeAccelerator::DecodeFromShmTask,
                                base::Unretained(this), bitstream_buffer.id(),
                                std::move(shm), std::move(video_frame)));
}

void VaapiMjpegDecodeAccelerator::Decode(int32_t task_id,
                                         base::ScopedFD src_dmabuf_fd,
                                         size_t src_size,
                                         off_t src_offset,
                                         scoped_refptr<VideoFrame> dst_frame) {
  DCHECK(io_task_runner_->BelongsToCurrentThread());
  TRACE_EVENT1("jpeg", __func__, "task_id", task_id);

  if (task_id < 0) {
    VLOGF(1) << "Invalid task id: " << task_id;
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }

  // Validate input arguments.
  if (!src_dmabuf_fd.is_valid()) {
    VLOGF(1) << "Invalid input buffer FD";
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }
  if (src_size == 0) {
    VLOGF(1) << "Input buffer size is zero";
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }
  const size_t page_size = base::GetPageSize();
  if (src_offset < 0 || src_offset % page_size != 0) {
    VLOGF(1) << "Input buffer offset (" << src_offset
             << ") should be non-negative and aligned to page size ("
             << page_size << ")";
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }

  // Validate output video frame.
  if (!dst_frame->IsMappable() && !dst_frame->HasDmaBufs()) {
    VLOGF(1) << "Unsupported output frame storage type";
    NotifyError(task_id, INVALID_ARGUMENT);
    return;
  }
  if ((dst_frame->visible_rect().width() & 1) ||
      (dst_frame->visible_rect().height() & 1)) {
    VLOGF(1) << "Output frame visible size has odd dimension";
    NotifyError(task_id, PLATFORM_FAILURE);
    return;
  }

  // It's safe to use base::Unretained(this) because |decoder_task_runner_| runs
  // tasks on |decoder_thread_| which is stopped in the destructor of |this|.
  decoder_task_runner_->PostTask(
      FROM_HERE,
      base::BindOnce(&VaapiMjpegDecodeAccelerator::DecodeFromDmaBufTask,
                     base::Unretained(this), task_id, std::move(src_dmabuf_fd),
                     src_size, src_offset, std::move(dst_frame)));
}

bool VaapiMjpegDecodeAccelerator::IsSupported() {
  return VaapiWrapper::IsDecodeSupported(VAProfileJPEGBaseline);
}

}  // namespace media
