- add sources.
[platform/framework/web/crosswalk.git] / src / media / filters / gpu_video_decoder.h
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_FILTERS_GPU_VIDEO_DECODER_H_
6 #define MEDIA_FILTERS_GPU_VIDEO_DECODER_H_
7
8 #include <list>
9 #include <map>
10 #include <set>
11 #include <utility>
12 #include <vector>
13
14 #include "base/memory/weak_ptr.h"
15 #include "media/base/pipeline_status.h"
16 #include "media/base/video_decoder.h"
17 #include "media/video/video_decode_accelerator.h"
18
19 template <class T> class scoped_refptr;
20
21 namespace base {
22 class MessageLoopProxy;
23 class SharedMemory;
24 }
25
26 namespace media {
27
28 class DecoderBuffer;
29 class GpuVideoAcceleratorFactories;
30 class MediaLog;
31
32 // GPU-accelerated video decoder implementation.  Relies on
33 // AcceleratedVideoDecoderMsg_Decode and friends.
34 class MEDIA_EXPORT GpuVideoDecoder
35     : public VideoDecoder,
36       public VideoDecodeAccelerator::Client {
37  public:
38   // The message loop of |factories| will be saved to |gvd_loop_proxy_|.
39   explicit GpuVideoDecoder(
40       const scoped_refptr<GpuVideoAcceleratorFactories>& factories,
41       const scoped_refptr<MediaLog>& media_log);
42
43   // VideoDecoder implementation.
44   virtual void Initialize(const VideoDecoderConfig& config,
45                           const PipelineStatusCB& status_cb) OVERRIDE;
46   virtual void Decode(const scoped_refptr<DecoderBuffer>& buffer,
47                       const DecodeCB& decode_cb) OVERRIDE;
48   virtual void Reset(const base::Closure& closure) OVERRIDE;
49   virtual void Stop(const base::Closure& closure) OVERRIDE;
50   virtual bool HasAlpha() const OVERRIDE;
51   virtual bool NeedsBitstreamConversion() const OVERRIDE;
52   virtual bool CanReadWithoutStalling() const OVERRIDE;
53
54   // VideoDecodeAccelerator::Client implementation.
55   virtual void NotifyInitializeDone() OVERRIDE;
56   virtual void ProvidePictureBuffers(uint32 count,
57                                      const gfx::Size& size,
58                                      uint32 texture_target) OVERRIDE;
59   virtual void DismissPictureBuffer(int32 id) OVERRIDE;
60   virtual void PictureReady(const media::Picture& picture) OVERRIDE;
61   virtual void NotifyEndOfBitstreamBuffer(int32 id) OVERRIDE;
62   virtual void NotifyFlushDone() OVERRIDE;
63   virtual void NotifyResetDone() OVERRIDE;
64   virtual void NotifyError(media::VideoDecodeAccelerator::Error error) OVERRIDE;
65
66  protected:
67   virtual ~GpuVideoDecoder();
68
69  private:
70   enum State {
71     kNormal,
72     kDrainingDecoder,
73     kDecoderDrained,
74     kError
75   };
76
77   // A shared memory segment and its allocated size.
78   struct SHMBuffer {
79     SHMBuffer(base::SharedMemory* m, size_t s);
80     ~SHMBuffer();
81     base::SharedMemory* shm;
82     size_t size;
83   };
84
85   // A SHMBuffer and the DecoderBuffer its data came from.
86   struct BufferPair {
87     BufferPair(SHMBuffer* s, const scoped_refptr<DecoderBuffer>& b);
88     ~BufferPair();
89     SHMBuffer* shm_buffer;
90     scoped_refptr<DecoderBuffer> buffer;
91   };
92
93   typedef std::map<int32, PictureBuffer> PictureBufferMap;
94
95   // Return true if more decode work can be piled on to the VDA.
96   bool CanMoreDecodeWorkBeDone();
97
98   // Enqueue a frame for later delivery (or drop it on the floor if a
99   // vda->Reset() is in progress) and trigger out-of-line delivery of the oldest
100   // ready frame to the client if there is a pending read.  A NULL |frame|
101   // merely triggers delivery, and requires the ready_video_frames_ queue not be
102   // empty.
103   void EnqueueFrameAndTriggerFrameDelivery(
104       const scoped_refptr<VideoFrame>& frame);
105
106   // Indicate the picture buffer can be reused by the decoder.
107   void ReusePictureBuffer(int64 picture_buffer_id, uint32 sync_point);
108
109   void RecordBufferData(
110       const BitstreamBuffer& bitstream_buffer, const DecoderBuffer& buffer);
111   void GetBufferData(int32 id, base::TimeDelta* timetamp,
112                      gfx::Rect* visible_rect, gfx::Size* natural_size);
113
114   void DestroyVDA();
115
116   // Request a shared-memory segment of at least |min_size| bytes.  Will
117   // allocate as necessary.  Caller does not own returned pointer.
118   SHMBuffer* GetSHM(size_t min_size);
119
120   // Return a shared-memory segment to the available pool.
121   void PutSHM(SHMBuffer* shm_buffer);
122
123   // Destroy all PictureBuffers in |buffers|, and delete their textures.
124   void DestroyPictureBuffers(PictureBufferMap* buffers);
125
126   bool needs_bitstream_conversion_;
127
128   // Message loop which this class and |factories_| run on.
129   scoped_refptr<base::MessageLoopProxy> gvd_loop_proxy_;
130   base::WeakPtrFactory<GpuVideoDecoder> weak_factory_;
131   base::WeakPtr<GpuVideoDecoder> weak_this_;
132
133   scoped_refptr<GpuVideoAcceleratorFactories> factories_;
134
135   // Populated during Initialize() (on success) and unchanged until an error
136   // occurs.
137   scoped_ptr<VideoDecodeAccelerator> vda_;
138
139   // Callbacks that are !is_null() only during their respective operation being
140   // asynchronously executed.
141   DecodeCB pending_decode_cb_;
142   base::Closure pending_reset_cb_;
143
144   State state_;
145
146   VideoDecoderConfig config_;
147
148   // Shared-memory buffer pool.  Since allocating SHM segments requires a
149   // round-trip to the browser process, we keep allocation out of the
150   // steady-state of the decoder.
151   std::vector<SHMBuffer*> available_shm_segments_;
152
153   scoped_refptr<MediaLog> media_log_;
154
155   std::map<int32, BufferPair> bitstream_buffers_in_decoder_;
156   PictureBufferMap assigned_picture_buffers_;
157   PictureBufferMap dismissed_picture_buffers_;
158   // PictureBuffers given to us by VDA via PictureReady, which we sent forward
159   // as VideoFrames to be rendered via decode_cb_, and which will be returned
160   // to us via ReusePictureBuffer.
161   std::set<int32> picture_buffers_at_display_;
162
163   // The texture target used for decoded pictures.
164   uint32 decoder_texture_target_;
165
166   struct BufferData {
167     BufferData(int32 bbid, base::TimeDelta ts, const gfx::Rect& visible_rect,
168                const gfx::Size& natural_size);
169     ~BufferData();
170     int32 bitstream_buffer_id;
171     base::TimeDelta timestamp;
172     gfx::Rect visible_rect;
173     gfx::Size natural_size;
174   };
175   std::list<BufferData> input_buffer_data_;
176
177   // picture_buffer_id and the frame wrapping the corresponding Picture, for
178   // frames that have been decoded but haven't been requested by a Decode() yet.
179   std::list<scoped_refptr<VideoFrame> > ready_video_frames_;
180   int32 next_picture_buffer_id_;
181   int32 next_bitstream_buffer_id_;
182
183   // Set during ProvidePictureBuffers(), used for checking and implementing
184   // HasAvailableOutputFrames().
185   int available_pictures_;
186
187   DISALLOW_COPY_AND_ASSIGN(GpuVideoDecoder);
188 };
189
190 }  // namespace media
191
192 #endif  // MEDIA_FILTERS_GPU_VIDEO_DECODER_H_