Home | History | Annotate | Download | only in base
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #ifndef MEDIA_BASE_VIDEO_FRAME_H_
      6 #define MEDIA_BASE_VIDEO_FRAME_H_
      7 
      8 #include "base/callback.h"
      9 #include "base/md5.h"
     10 #include "base/memory/shared_memory.h"
     11 #include "gpu/command_buffer/common/mailbox.h"
     12 #include "media/base/buffers.h"
     13 #include "ui/gfx/rect.h"
     14 #include "ui/gfx/size.h"
     15 
     16 class SkBitmap;
     17 
     18 namespace media {
     19 
     20 class MEDIA_EXPORT VideoFrame : public base::RefCountedThreadSafe<VideoFrame> {
     21  public:
     22   enum {
     23     kFrameSizeAlignment = 16,
     24     kFrameSizePadding = 16,
     25     kFrameAddressAlignment = 32
     26   };
     27 
     28   enum {
     29     kMaxPlanes = 4,
     30 
     31     kYPlane = 0,
     32     kUPlane = 1,
     33     kVPlane = 2,
     34     kAPlane = 3,
     35   };
     36 
     37   // Surface formats roughly based on FOURCC labels, see:
     38   // http://www.fourcc.org/rgb.php
     39   // http://www.fourcc.org/yuv.php
     40   // Logged to UMA, so never reuse values.
     41   enum Format {
     42     UNKNOWN = 0,  // Unknown format value.
     43     YV12 = 1,  // 12bpp YVU planar 1x1 Y, 2x2 VU samples
     44     YV16 = 2,  // 16bpp YVU planar 1x1 Y, 2x1 VU samples
     45     I420 = 3,  // 12bpp YVU planar 1x1 Y, 2x2 UV samples.
     46     YV12A = 4,  // 20bpp YUVA planar 1x1 Y, 2x2 VU, 1x1 A samples.
     47 #if defined(VIDEO_HOLE)
     48     HOLE = 5,  // Hole frame.
     49 #endif  // defined(VIDEO_HOLE)
     50     NATIVE_TEXTURE = 6,  // Native texture.  Pixel-format agnostic.
     51     YV12J = 7,  // JPEG color range version of YV12
     52     HISTOGRAM_MAX,  // Must always be greatest.
     53   };
     54 
     55   // Returns the name of a Format as a string.
     56   static std::string FormatToString(Format format);
     57 
     58   // This class calls the TextureNoLongerNeededCallback when this class is
     59   // destroyed.  Users can query the current sync point associated with this
     60   // mailbox with sync_point(), and should call Resync() with a new sync point
     61   // to ensure the mailbox remains valid for the issued commands.
     62   // valid for the issued commands.
     63   class MEDIA_EXPORT MailboxHolder {
     64    public:
     65     typedef base::Callback<void(uint32 sync_point)>
     66         TextureNoLongerNeededCallback;
     67 
     68     MailboxHolder(const gpu::Mailbox& mailbox,
     69                   unsigned sync_point,
     70                   const TextureNoLongerNeededCallback& release_callback);
     71     ~MailboxHolder();
     72 
     73     const gpu::Mailbox& mailbox() const { return mailbox_; }
     74     unsigned sync_point() const { return sync_point_; }
     75 
     76     void Resync(unsigned sync_point) { sync_point_ = sync_point; }
     77 
     78    private:
     79 
     80     gpu::Mailbox mailbox_;
     81     unsigned sync_point_;
     82     TextureNoLongerNeededCallback release_callback_;
     83   };
     84 
     85 
     86   // Creates a new frame in system memory with given parameters. Buffers for
     87   // the frame are allocated but not initialized.
     88   // |coded_size| is the width and height of the frame data in pixels.
     89   // |visible_rect| is the visible portion of |coded_size|, after cropping (if
     90   // any) is applied.
     91   // |natural_size| is the width and height of the frame when the frame's aspect
     92   // ratio is applied to |visible_rect|.
     93   static scoped_refptr<VideoFrame> CreateFrame(
     94       Format format,
     95       const gfx::Size& coded_size,
     96       const gfx::Rect& visible_rect,
     97       const gfx::Size& natural_size,
     98       base::TimeDelta timestamp);
     99 
    100   // Call prior to CreateFrame to ensure validity of frame configuration. Called
    101   // automatically by VideoDecoderConfig::IsValidConfig().
    102   // TODO(scherkus): VideoDecoderConfig shouldn't call this method
    103   static bool IsValidConfig(Format format, const gfx::Size& coded_size,
    104                             const gfx::Rect& visible_rect,
    105                             const gfx::Size& natural_size);
    106 
    107   // CB to write pixels from the texture backing this frame into the
    108   // |const SkBitmap&| parameter.
    109   typedef base::Callback<void(const SkBitmap&)> ReadPixelsCB;
    110 
    111   // Wraps a native texture of the given parameters with a VideoFrame.  When the
    112   // frame is destroyed |no_longer_needed_cb.Run()| will be called.
    113   // |coded_size| is the width and height of the frame data in pixels.
    114   // |visible_rect| is the visible portion of |coded_size|, after cropping (if
    115   // any) is applied.
    116   // |natural_size| is the width and height of the frame when the frame's aspect
    117   // ratio is applied to |visible_rect|.
    118 
    119   // |read_pixels_cb| may be used to do (slow!) readbacks from the
    120   // texture to main memory.
    121   static scoped_refptr<VideoFrame> WrapNativeTexture(
    122       scoped_ptr<MailboxHolder> mailbox_holder,
    123       uint32 texture_target,
    124       const gfx::Size& coded_size,
    125       const gfx::Rect& visible_rect,
    126       const gfx::Size& natural_size,
    127       base::TimeDelta timestamp,
    128       const ReadPixelsCB& read_pixels_cb,
    129       const base::Closure& no_longer_needed_cb);
    130 
    131   // Read pixels from the native texture backing |*this| and write
    132   // them to |pixels| as BGRA.  |pixels| must point to a buffer at
    133   // least as large as 4*visible_rect().width()*visible_rect().height().
    134   void ReadPixelsFromNativeTexture(const SkBitmap& pixels);
    135 
    136   // Wraps packed image data residing in a memory buffer with a VideoFrame.
    137   // The image data resides in |data| and is assumed to be packed tightly in a
    138   // buffer of logical dimensions |coded_size| with the appropriate bit depth
    139   // and plane count as given by |format|.  The shared memory handle of the
    140   // backing allocation, if present, can be passed in with |handle|.  When the
    141   // frame is destroyed, |no_longer_needed_cb.Run()| will be called.
    142   static scoped_refptr<VideoFrame> WrapExternalPackedMemory(
    143       Format format,
    144       const gfx::Size& coded_size,
    145       const gfx::Rect& visible_rect,
    146       const gfx::Size& natural_size,
    147       uint8* data,
    148       size_t data_size,
    149       base::SharedMemoryHandle handle,
    150       base::TimeDelta timestamp,
    151       const base::Closure& no_longer_needed_cb);
    152 
    153   // Wraps external YUV data of the given parameters with a VideoFrame.
    154   // The returned VideoFrame does not own the data passed in. When the frame
    155   // is destroyed |no_longer_needed_cb.Run()| will be called.
    156   // TODO(sheu): merge this into WrapExternalSharedMemory().
    157   // http://crbug.com/270217
    158   static scoped_refptr<VideoFrame> WrapExternalYuvData(
    159       Format format,
    160       const gfx::Size& coded_size,
    161       const gfx::Rect& visible_rect,
    162       const gfx::Size& natural_size,
    163       int32 y_stride,
    164       int32 u_stride,
    165       int32 v_stride,
    166       uint8* y_data,
    167       uint8* u_data,
    168       uint8* v_data,
    169       base::TimeDelta timestamp,
    170       const base::Closure& no_longer_needed_cb);
    171 
    172   // Wraps |frame| and calls |no_longer_needed_cb| when the wrapper VideoFrame
    173   // gets destroyed.
    174   static scoped_refptr<VideoFrame> WrapVideoFrame(
    175       const scoped_refptr<VideoFrame>& frame,
    176       const base::Closure& no_longer_needed_cb);
    177 
    178   // Creates a frame which indicates end-of-stream.
    179   static scoped_refptr<VideoFrame> CreateEOSFrame();
    180 
    181   // Allocates YV12 frame based on |size|, and sets its data to the YUV(y,u,v).
    182   static scoped_refptr<VideoFrame> CreateColorFrame(
    183       const gfx::Size& size,
    184       uint8 y, uint8 u, uint8 v,
    185       base::TimeDelta timestamp);
    186 
    187   // Allocates YV12 frame based on |size|, and sets its data to the YUV
    188   // equivalent of RGB(0,0,0).
    189   static scoped_refptr<VideoFrame> CreateBlackFrame(const gfx::Size& size);
    190 
    191 #if defined(VIDEO_HOLE)
    192   // Allocates a hole frame.
    193   static scoped_refptr<VideoFrame> CreateHoleFrame(const gfx::Size& size);
    194 #endif  // defined(VIDEO_HOLE)
    195 
    196   static size_t NumPlanes(Format format);
    197 
    198   // Returns the required allocation size for a (tightly packed) frame of the
    199   // given coded size and format.
    200   static size_t AllocationSize(Format format, const gfx::Size& coded_size);
    201 
    202   // Returns the required allocation size for a (tightly packed) plane of the
    203   // given coded size and format.
    204   static size_t PlaneAllocationSize(Format format,
    205                                     size_t plane,
    206                                     const gfx::Size& coded_size);
    207 
    208   Format format() const { return format_; }
    209 
    210   const gfx::Size& coded_size() const { return coded_size_; }
    211   const gfx::Rect& visible_rect() const { return visible_rect_; }
    212   const gfx::Size& natural_size() const { return natural_size_; }
    213 
    214   int stride(size_t plane) const;
    215 
    216   // Returns the number of bytes per row and number of rows for a given plane.
    217   //
    218   // As opposed to stride(), row_bytes() refers to the bytes representing
    219   // frame data scanlines (coded_size.width() pixels, without stride padding).
    220   int row_bytes(size_t plane) const;
    221   int rows(size_t plane) const;
    222 
    223   // Returns pointer to the buffer for a given plane. The memory is owned by
    224   // VideoFrame object and must not be freed by the caller.
    225   uint8* data(size_t plane) const;
    226 
    227   // Returns the mailbox of the native texture wrapped by this frame. Only
    228   // valid to call if this is a NATIVE_TEXTURE frame. Before using the
    229   // mailbox, the caller must wait for the included sync point.
    230   MailboxHolder* texture_mailbox() const;
    231 
    232   // Returns the texture target. Only valid for NATIVE_TEXTURE frames.
    233   uint32 texture_target() const;
    234 
    235   // Returns the shared-memory handle, if present
    236   base::SharedMemoryHandle shared_memory_handle() const;
    237 
    238   // Returns true if this VideoFrame represents the end of the stream.
    239   bool end_of_stream() const { return end_of_stream_; }
    240 
    241   base::TimeDelta GetTimestamp() const {
    242     return timestamp_;
    243   }
    244   void SetTimestamp(const base::TimeDelta& timestamp) {
    245     timestamp_ = timestamp;
    246   }
    247 
    248   // Used to keep a running hash of seen frames.  Expects an initialized MD5
    249   // context.  Calls MD5Update with the context and the contents of the frame.
    250   void HashFrameForTesting(base::MD5Context* context);
    251 
    252  private:
    253   friend class base::RefCountedThreadSafe<VideoFrame>;
    254   // Clients must use the static CreateFrame() method to create a new frame.
    255   VideoFrame(Format format,
    256              const gfx::Size& coded_size,
    257              const gfx::Rect& visible_rect,
    258              const gfx::Size& natural_size,
    259              base::TimeDelta timestamp,
    260              bool end_of_stream);
    261   virtual ~VideoFrame();
    262 
    263   void AllocateYUV();
    264 
    265   // Used to DCHECK() plane parameters.
    266   bool IsValidPlane(size_t plane) const;
    267 
    268   // Frame format.
    269   Format format_;
    270 
    271   // Width and height of the video frame.
    272   gfx::Size coded_size_;
    273 
    274   // Width, height, and offsets of the visible portion of the video frame.
    275   gfx::Rect visible_rect_;
    276 
    277   // Width and height of the visible portion of the video frame with aspect
    278   // ratio taken into account.
    279   gfx::Size natural_size_;
    280 
    281   // Array of strides for each plane, typically greater or equal to the width
    282   // of the surface divided by the horizontal sampling period.  Note that
    283   // strides can be negative.
    284   int32 strides_[kMaxPlanes];
    285 
    286   // Array of data pointers to each plane.
    287   uint8* data_[kMaxPlanes];
    288 
    289   // Native texture mailbox, if this is a NATIVE_TEXTURE frame.
    290   scoped_ptr<MailboxHolder> texture_mailbox_holder_;
    291   uint32 texture_target_;
    292   ReadPixelsCB read_pixels_cb_;
    293 
    294   // Shared memory handle, if this frame was allocated from shared memory.
    295   base::SharedMemoryHandle shared_memory_handle_;
    296 
    297   base::Closure no_longer_needed_cb_;
    298 
    299   base::TimeDelta timestamp_;
    300 
    301   const bool end_of_stream_;
    302 
    303   DISALLOW_IMPLICIT_CONSTRUCTORS(VideoFrame);
    304 };
    305 
    306 }  // namespace media
    307 
    308 #endif  // MEDIA_BASE_VIDEO_FRAME_H_
    309