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