161 lines
6.5 KiB
C++
161 lines
6.5 KiB
C++
// Copyright 2018 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.
|
|
// Note: ported from Chromium commit head: 61df9350f6de
|
|
// Note: Added kNoModifier define to remove dependency on native pixmap handle.
|
|
|
|
#ifndef VIDEO_FRAME_LAYOUT_H_
|
|
#define VIDEO_FRAME_LAYOUT_H_
|
|
|
|
#include <stddef.h>
|
|
#include <stdint.h>
|
|
|
|
#include <ostream>
|
|
#include <string>
|
|
#include <utility>
|
|
#include <vector>
|
|
|
|
#include "base/optional.h"
|
|
#include "color_plane_layout.h"
|
|
#include "size.h"
|
|
#include "video_pixel_format.h"
|
|
|
|
namespace media {
|
|
|
|
// Copied from native_pixmap_handle.h:
|
|
// This is the same value as DRM_FORMAT_MOD_INVALID, which is not a valid
|
|
// modifier. We use this to indicate that layout information
|
|
// (tiling/compression) if any will be communicated out of band.
|
|
static constexpr uint64_t kNoModifier = 0x00ffffffffffffffULL;
|
|
|
|
// A class to describes how physical buffer is allocated for video frame.
|
|
// In stores format, coded size of the frame and size of physical buffers
|
|
// which can be used to allocate buffer(s) hardware expected.
|
|
// It also stores stride (bytes per line) and offset per color plane as Plane.
|
|
// stride is to calculate each color plane's size (note that a buffer may
|
|
// contains multiple color planes.)
|
|
// offset is to describe a start point of each plane from buffer's dmabuf fd.
|
|
// Note that it is copyable.
|
|
class VideoFrameLayout {
|
|
public:
|
|
// Default alignment for buffers.
|
|
// Note: This value is dependent on what's used by ffmpeg, do not change
|
|
// without inspecting av_frame_get_buffer() first.
|
|
static constexpr size_t kBufferAddressAlignment = 32;
|
|
|
|
// Factory functions.
|
|
// |format| and |coded_size| must always be specified.
|
|
// |planes| info is also optional but useful to represent the layout of a
|
|
// video frame buffer correctly. When omitted, its information is all set
|
|
// to zero, so clients should be wary not to use this information.
|
|
// |buffer_addr_align| can be specified to request a specific buffer memory
|
|
// alignment.
|
|
// |modifier| is the additional information of |format|. It will become some
|
|
// value else than gfx::NativePixmapHandle::kNoModifier when the underlying
|
|
// buffer format is different from a standard |format| due to tiling.
|
|
// The returned base::Optional will be base::nullopt if the configured values
|
|
// are invalid.
|
|
|
|
// Create a layout suitable for |format| at |coded_size|. The stride, offsets
|
|
// and size of all planes are set to 0, since that information cannot reliably
|
|
// be infered from the arguments.
|
|
static base::Optional<VideoFrameLayout> Create(VideoPixelFormat format,
|
|
const Size& coded_size);
|
|
|
|
// Create a layout suitable for |format| at |coded_size|, with the |strides|
|
|
// for each plane specified. The offsets and size of all planes are set to 0.
|
|
// The size of |strides| must be equal to NumPlanes(|format|).
|
|
static base::Optional<VideoFrameLayout> CreateWithStrides(
|
|
VideoPixelFormat format,
|
|
const Size& coded_size,
|
|
std::vector<int32_t> strides);
|
|
|
|
// Create a layout suitable for |format| at |coded_size|, with the |planes|
|
|
// fully provided.
|
|
// The size of |planes| must be equal to NumPlanes(|format|).
|
|
static base::Optional<VideoFrameLayout> CreateWithPlanes(
|
|
VideoPixelFormat format,
|
|
const Size& coded_size,
|
|
std::vector<ColorPlaneLayout> planes,
|
|
size_t buffer_addr_align = kBufferAddressAlignment,
|
|
uint64_t modifier = kNoModifier);
|
|
|
|
// This constructor should be called for situations where the frames using
|
|
// this format are backed by multiple physical buffers, instead of having each
|
|
// plane at different offsets of the same buffer. Currently only used by V4L2.
|
|
static base::Optional<VideoFrameLayout> CreateMultiPlanar(
|
|
VideoPixelFormat format,
|
|
const Size& coded_size,
|
|
std::vector<ColorPlaneLayout> planes,
|
|
size_t buffer_addr_align = kBufferAddressAlignment,
|
|
uint64_t modifier = kNoModifier);
|
|
|
|
VideoFrameLayout() = delete;
|
|
VideoFrameLayout(const VideoFrameLayout&);
|
|
VideoFrameLayout(VideoFrameLayout&&);
|
|
VideoFrameLayout& operator=(const VideoFrameLayout&);
|
|
~VideoFrameLayout();
|
|
|
|
static size_t NumPlanes(VideoPixelFormat format);
|
|
|
|
VideoPixelFormat format() const { return format_; }
|
|
const Size& coded_size() const { return coded_size_; }
|
|
|
|
// Returns number of planes. Note that num_planes >= num_buffers.
|
|
size_t num_planes() const { return planes_.size(); }
|
|
|
|
const std::vector<ColorPlaneLayout>& planes() const { return planes_; }
|
|
|
|
bool operator==(const VideoFrameLayout& rhs) const;
|
|
bool operator!=(const VideoFrameLayout& rhs) const;
|
|
|
|
// Return true when a format uses multiple backing buffers to store its
|
|
// planes.
|
|
bool is_multi_planar() const { return is_multi_planar_; }
|
|
// Returns the required memory alignment for buffers.
|
|
size_t buffer_addr_align() const { return buffer_addr_align_; }
|
|
// Return the modifier of buffers.
|
|
uint64_t modifier() const { return modifier_; }
|
|
|
|
private:
|
|
VideoFrameLayout(VideoPixelFormat format,
|
|
const Size& coded_size,
|
|
std::vector<ColorPlaneLayout> planes,
|
|
bool is_multi_planar,
|
|
size_t buffer_addr_align,
|
|
uint64_t modifier);
|
|
|
|
VideoPixelFormat format_;
|
|
|
|
// Width and height of the video frame in pixels. This must include pixel
|
|
// data for the whole image; i.e. for YUV formats with subsampled chroma
|
|
// planes, in the case that the visible portion of the image does not line up
|
|
// on a sample boundary, |coded_size_| must be rounded up appropriately and
|
|
// the pixel data provided for the odd pixels.
|
|
Size coded_size_;
|
|
|
|
// Layout property for each color planes, e.g. stride and buffer offset.
|
|
std::vector<ColorPlaneLayout> planes_;
|
|
|
|
// Set to true when a format uses multiple backing buffers to store its
|
|
// planes. Used by code for V4L2 API at the moment.
|
|
bool is_multi_planar_;
|
|
|
|
// Memory address alignment of the buffers. This is only relevant when
|
|
// allocating physical memory for the buffer, so it doesn't need to be
|
|
// serialized when frames are passed through Mojo.
|
|
size_t buffer_addr_align_;
|
|
|
|
// Modifier of buffers. The modifier is retrieved from GBM library. This
|
|
// can be a different value from kNoModifier only if the VideoFrame is created
|
|
// by using NativePixmap.
|
|
uint64_t modifier_;
|
|
};
|
|
|
|
// Outputs VideoFrameLayout to stream.
|
|
std::ostream& operator<<(std::ostream& ostream, const VideoFrameLayout& layout);
|
|
|
|
} // namespace media
|
|
|
|
#endif // VIDEO_FRAME_LAYOUT_H_
|