Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(46)

Side by Side Diff: media/gpu/android_video_decode_accelerator.h

Issue 2508053002: media: Do a TimedWait() for video surface teardown in AVDA (Closed)
Patch Set: change timeout to 2 Created 4 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « media/gpu/BUILD.gn ('k') | media/gpu/android_video_decode_accelerator.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #ifndef MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_ 5 #ifndef MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_
6 #define MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_ 6 #define MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_
7 7
8 #include <stdint.h> 8 #include <stdint.h>
9 9
10 #include <list> 10 #include <list>
11 #include <map> 11 #include <map>
12 #include <queue> 12 #include <queue>
13 #include <vector> 13 #include <vector>
14 14
15 #include "base/compiler_specific.h" 15 #include "base/compiler_specific.h"
16 #include "base/optional.h" 16 #include "base/optional.h"
17 #include "base/threading/thread_checker.h" 17 #include "base/threading/thread_checker.h"
18 #include "base/timer/timer.h" 18 #include "base/timer/timer.h"
19 #include "gpu/command_buffer/service/gles2_cmd_decoder.h" 19 #include "gpu/command_buffer/service/gles2_cmd_decoder.h"
20 #include "gpu/command_buffer/service/gpu_preferences.h" 20 #include "gpu/command_buffer/service/gpu_preferences.h"
21 #include "media/base/android/media_drm_bridge_cdm_context.h" 21 #include "media/base/android/media_drm_bridge_cdm_context.h"
22 #include "media/base/android/sdk_media_codec_bridge.h" 22 #include "media/base/android/sdk_media_codec_bridge.h"
23 #include "media/base/media_keys.h" 23 #include "media/base/media_keys.h"
24 #include "media/gpu/avda_codec_allocator.h" 24 #include "media/gpu/avda_codec_allocator.h"
25 #include "media/gpu/avda_picture_buffer_manager.h" 25 #include "media/gpu/avda_picture_buffer_manager.h"
26 #include "media/gpu/avda_state_provider.h" 26 #include "media/gpu/avda_state_provider.h"
27 #include "media/gpu/avda_surface_tracker.h"
28 #include "media/gpu/gpu_video_decode_accelerator_helpers.h" 27 #include "media/gpu/gpu_video_decode_accelerator_helpers.h"
29 #include "media/gpu/media_gpu_export.h" 28 #include "media/gpu/media_gpu_export.h"
30 #include "media/video/video_decode_accelerator.h" 29 #include "media/video/video_decode_accelerator.h"
31 #include "ui/gl/android/scoped_java_surface.h" 30 #include "ui/gl/android/scoped_java_surface.h"
32 31
33 namespace gl {
34 class SurfaceTexture;
35 }
36
37 namespace media { 32 namespace media {
38 class SharedMemoryRegion; 33 class SharedMemoryRegion;
39 34
40 // A VideoDecodeAccelerator implementation for Android. This class decodes the 35 // A VideoDecodeAccelerator implementation for Android. This class decodes the
41 // encded input stream using Android's MediaCodec. It handles the work of 36 // encded input stream using Android's MediaCodec. It handles the work of
42 // transferring data to and from MediaCodec, and delegates attaching MediaCodec 37 // transferring data to and from MediaCodec, and delegates attaching MediaCodec
43 // output buffers to PictureBuffers to AVDAPictureBufferManager. 38 // output buffers to PictureBuffers to AVDAPictureBufferManager.
44 class MEDIA_GPU_EXPORT AndroidVideoDecodeAccelerator 39 class MEDIA_GPU_EXPORT AndroidVideoDecodeAccelerator
45 : public VideoDecodeAccelerator, 40 : public VideoDecodeAccelerator,
46 public AVDAStateProvider { 41 public AVDAStateProvider,
42 public AVDACodecAllocatorClient {
47 public: 43 public:
48 static VideoDecodeAccelerator::Capabilities GetCapabilities( 44 static VideoDecodeAccelerator::Capabilities GetCapabilities(
49 const gpu::GpuPreferences& gpu_preferences); 45 const gpu::GpuPreferences& gpu_preferences);
50 46
51 AndroidVideoDecodeAccelerator( 47 AndroidVideoDecodeAccelerator(
52 const MakeGLContextCurrentCallback& make_context_current_cb, 48 const MakeGLContextCurrentCallback& make_context_current_cb,
53 const GetGLES2DecoderCallback& get_gles2_decoder_cb); 49 const GetGLES2DecoderCallback& get_gles2_decoder_cb);
54 50
55 ~AndroidVideoDecodeAccelerator() override; 51 ~AndroidVideoDecodeAccelerator() override;
56 52
(...skipping 10 matching lines...) Expand all
67 const base::WeakPtr<Client>& decode_client, 63 const base::WeakPtr<Client>& decode_client,
68 const scoped_refptr<base::SingleThreadTaskRunner>& decode_task_runner) 64 const scoped_refptr<base::SingleThreadTaskRunner>& decode_task_runner)
69 override; 65 override;
70 66
71 // AVDAStateProvider implementation: 67 // AVDAStateProvider implementation:
72 const gfx::Size& GetSize() const override; 68 const gfx::Size& GetSize() const override;
73 base::WeakPtr<gpu::gles2::GLES2Decoder> GetGlDecoder() const override; 69 base::WeakPtr<gpu::gles2::GLES2Decoder> GetGlDecoder() const override;
74 // Notifies the client about the error and sets |state_| to |ERROR|. 70 // Notifies the client about the error and sets |state_| to |ERROR|.
75 void NotifyError(Error error) override; 71 void NotifyError(Error error) override;
76 72
73 // AVDACodecAllocatorClient implementation:
74 void OnSurfaceAvailable(bool success) override;
75 void OnSurfaceDestroyed() override;
76 void OnCodecConfigured(
77 std::unique_ptr<VideoCodecBridge> media_codec) override;
78
77 private: 79 private:
78 friend class AVDAManager; 80 friend class AVDAManager;
79 81
80 // TODO(timav): evaluate the need for more states in the AVDA state machine. 82 // TODO(timav): evaluate the need for more states in the AVDA state machine.
81 enum State { 83 enum State {
82 NO_ERROR, 84 NO_ERROR,
83 ERROR, 85 ERROR,
84 // Set when we are asynchronously constructing the codec. Will transition 86 // Set when we are asynchronously constructing the codec. Will transition
85 // to NO_ERROR or ERROR depending on success. 87 // to NO_ERROR or ERROR depending on success.
86 WAITING_FOR_CODEC, 88 WAITING_FOR_CODEC,
87 // Set when we have a codec, but it doesn't yet have a key. 89 // Set when we have a codec, but it doesn't yet have a key.
88 WAITING_FOR_KEY, 90 WAITING_FOR_KEY,
89 // The output surface was destroyed. We must not configure a new MediaCodec 91 // The output surface was destroyed. We must not configure a new MediaCodec
90 // with the destroyed surface. 92 // with the destroyed surface.
91 SURFACE_DESTROYED, 93 SURFACE_DESTROYED,
92 }; 94 };
93 95
94 enum DrainType { 96 enum DrainType {
95 DRAIN_TYPE_NONE, 97 DRAIN_TYPE_NONE,
96 DRAIN_FOR_FLUSH, 98 DRAIN_FOR_FLUSH,
97 DRAIN_FOR_RESET, 99 DRAIN_FOR_RESET,
98 DRAIN_FOR_DESTROY, 100 DRAIN_FOR_DESTROY,
99 }; 101 };
100 102
101 // Configuration info for MediaCodec.
102 // This is used to shuttle configuration info between threads without needing
103 // to worry about the lifetime of the AVDA instance. All of these should not
104 // be modified while |state_| is WAITING_FOR_CODEC.
105 class CodecConfig : public base::RefCountedThreadSafe<CodecConfig> {
106 public:
107 CodecConfig();
108
109 // Codec type. Used when we configure media codec.
110 VideoCodec codec_ = kUnknownVideoCodec;
111
112 // Whether encryption scheme requires to use protected surface.
113 bool needs_protected_surface_ = false;
114
115 // The surface that MediaCodec is configured to output to.
116 gl::ScopedJavaSurface surface_;
117
118 // The MediaCrypto object is used in the MediaCodec.configure() in case of
119 // an encrypted stream.
120 MediaDrmBridgeCdmContext::JavaObjectPtr media_crypto_;
121
122 // Initial coded size. The actual size might change at any time, so this
123 // is only a hint.
124 gfx::Size initial_expected_coded_size_;
125
126 // The type of allocation to use for this. We use this to select the right
127 // thread for construction / destruction, and to decide if we should
128 // restrict the codec to be software only.
129 AVDACodecAllocator::TaskType task_type_;
130
131 // Codec specific data (SPS and PPS for H264).
132 std::vector<uint8_t> csd0_;
133 std::vector<uint8_t> csd1_;
134
135 protected:
136 friend class base::RefCountedThreadSafe<CodecConfig>;
137 virtual ~CodecConfig();
138
139 private:
140 DISALLOW_COPY_AND_ASSIGN(CodecConfig);
141 };
142
143 // Callback that is called when the SurfaceView becomes available, if it's
144 // not during Initialize. |success| is true if it is now available, false
145 // if initialization should stop.
146 void OnSurfaceAvailable(bool success);
147
148 // Initialize of the picture buffer manager. This is to be called when the 103 // Initialize of the picture buffer manager. This is to be called when the
149 // SurfaceView in |surface_id_|, if any, is no longer busy. It will return 104 // SurfaceView in |surface_id_|, if any, is no longer busy. It will return
150 // false on failure, and true if initialization was successful. This includes 105 // false on failure, and true if initialization was successful. This includes
151 // synchronous and asynchronous init; the AVDA might not yet have a codec on 106 // synchronous and asynchronous init; the AVDA might not yet have a codec on
152 // success, but async init will at least be in progress. 107 // success, but async init will at least be in progress.
153 bool InitializePictureBufferManager(); 108 bool InitializePictureBufferManager();
154 109
155 // A part of destruction process that is sometimes postponed after the drain. 110 // A part of destruction process that is sometimes postponed after the drain.
156 void ActualDestroy(); 111 void ActualDestroy();
157 112
158 // Configures |media_codec_| with the given codec parameters from the client. 113 // Configures |media_codec_| with the given codec parameters from the client.
159 // This configuration will (probably) not be complete before this call 114 // This configuration will (probably) not be complete before this call
160 // returns. Multiple calls before completion will be ignored. |state_| 115 // returns. Multiple calls before completion will be ignored. |state_|
161 // must be NO_ERROR or WAITING_FOR_CODEC. Note that, once you call this, 116 // must be NO_ERROR or WAITING_FOR_CODEC. Note that, once you call this,
162 // you should be careful to avoid modifying members of |codec_config_| until 117 // you should be careful to avoid modifying members of |codec_config_| until
163 // |state_| is no longer WAITING_FOR_CODEC. 118 // |state_| is no longer WAITING_FOR_CODEC.
164 void ConfigureMediaCodecAsynchronously(); 119 void ConfigureMediaCodecAsynchronously();
165 120
166 // Like ConfigureMediaCodecAsynchronously, but synchronous. Returns true if 121 // Like ConfigureMediaCodecAsynchronously, but synchronous. Returns true if
167 // and only if |media_codec_| is non-null. Since all configuration is done 122 // and only if |media_codec_| is non-null. Since all configuration is done
168 // synchronously, there is no concern with modifying |codec_config_| after 123 // synchronously, there is no concern with modifying |codec_config_| after
169 // this returns. 124 // this returns.
170 bool ConfigureMediaCodecSynchronously(); 125 bool ConfigureMediaCodecSynchronously();
171 126
172 // Instantiate a media codec using |codec_config|. 127 // Instantiate a media codec using |codec_config|.
173 // This may be called on any thread. 128 // This may be called on any thread.
174 static std::unique_ptr<VideoCodecBridge> ConfigureMediaCodecOnAnyThread( 129 static std::unique_ptr<VideoCodecBridge> ConfigureMediaCodecOnAnyThread(
175 scoped_refptr<CodecConfig> codec_config); 130 scoped_refptr<CodecConfig> codec_config);
176 131
177 // Called on the main thread to update |media_codec_| and complete codec
178 // configuration. |media_codec| will be null if configuration failed.
179 void OnCodecConfigured(std::unique_ptr<VideoCodecBridge> media_codec);
180
181 // Sends the decoded frame specified by |codec_buffer_index| to the client. 132 // Sends the decoded frame specified by |codec_buffer_index| to the client.
182 void SendDecodedFrameToClient(int32_t codec_buffer_index, 133 void SendDecodedFrameToClient(int32_t codec_buffer_index,
183 int32_t bitstream_id); 134 int32_t bitstream_id);
184 135
185 // Does pending IO tasks if any. Once this is called, it polls |media_codec_| 136 // Does pending IO tasks if any. Once this is called, it polls |media_codec_|
186 // until it finishes pending tasks. For the polling, |kDecodePollDelay| is 137 // until it finishes pending tasks. For the polling, |kDecodePollDelay| is
187 // used. 138 // used.
188 void DoIOTask(bool start_timer); 139 void DoIOTask(bool start_timer);
189 140
190 // Feeds input data to |media_codec_|. This checks 141 // Feeds input data to |media_codec_|. This checks
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
228 void NotifyFlushDone(); 179 void NotifyFlushDone();
229 180
230 // Notifies the client that the decoder was reset. 181 // Notifies the client that the decoder was reset.
231 void NotifyResetDone(); 182 void NotifyResetDone();
232 183
233 // Start or stop our work-polling timer based on whether we did any work, and 184 // Start or stop our work-polling timer based on whether we did any work, and
234 // how long it has been since we've done work. Calling this with true will 185 // how long it has been since we've done work. Calling this with true will
235 // start the timer. Calling it with false may stop the timer. 186 // start the timer. Calling it with false may stop the timer.
236 void ManageTimer(bool did_work); 187 void ManageTimer(bool did_work);
237 188
238 // Safely clear |media_codec_|. Do this instead of calling reset() / assign.
239 // Otherwise, the destructor can hang if mediaserver is in a bad state. This
240 // will release immediately if safe, else post to a separate thread. Either
241 // way, |media_codec_| will be null upon return.
242 void ReleaseMediaCodec();
243
244 // Start the MediaCodec drain process by adding end_of_stream() buffer to the 189 // Start the MediaCodec drain process by adding end_of_stream() buffer to the
245 // encoded buffers queue. When we receive EOS from the output buffer the drain 190 // encoded buffers queue. When we receive EOS from the output buffer the drain
246 // process completes and we perform the action depending on the |drain_type|. 191 // process completes and we perform the action depending on the |drain_type|.
247 void StartCodecDrain(DrainType drain_type); 192 void StartCodecDrain(DrainType drain_type);
248 193
249 // Returns true if we are currently draining the codec and doing that as part 194 // Returns true if we are currently draining the codec and doing that as part
250 // of Reset() or Destroy() VP8 workaround. (http://crbug.com/598963). We won't 195 // of Reset() or Destroy() VP8 workaround. (http://crbug.com/598963). We won't
251 // display any frames and disable normal errors handling. 196 // display any frames and disable normal errors handling.
252 bool IsDrainingForResetOrDestroy() const; 197 bool IsDrainingForResetOrDestroy() const;
253 198
254 // A helper method that performs the operation required after the drain 199 // A helper method that performs the operation required after the drain
255 // completion (usually when we receive EOS in the output). The operation 200 // completion (usually when we receive EOS in the output). The operation
256 // itself depends on the |drain_type_|. 201 // itself depends on the |drain_type_|.
257 void OnDrainCompleted(); 202 void OnDrainCompleted();
258 203
259 // Resets MediaCodec and buffers/containers used for storing output. These 204 // Resets MediaCodec and buffers/containers used for storing output. These
260 // components need to be reset upon EOS to decode a later stream. Input state 205 // components need to be reset upon EOS to decode a later stream. Input state
261 // (e.g. queued BitstreamBuffers) is not reset, as input following an EOS 206 // (e.g. queued BitstreamBuffers) is not reset, as input following an EOS
262 // is still valid and should be processed. 207 // is still valid and should be processed.
263 void ResetCodecState(); 208 void ResetCodecState();
264 209
265 // Registered to be called when surfaces are being destroyed. If |surface_id|
266 // is our surface, we should release the MediaCodec before returning from
267 // this.
268 void OnDestroyingSurface(int surface_id);
269
270 // Indicates if MediaCodec should not be used for software decoding since we 210 // Indicates if MediaCodec should not be used for software decoding since we
271 // have safer versions elsewhere. 211 // have safer versions elsewhere.
272 bool IsMediaCodecSoftwareDecodingForbidden() const; 212 bool IsMediaCodecSoftwareDecodingForbidden() const;
273 213
274 // On platforms which support seamless surface changes, this will reinitialize 214 // On platforms which support seamless surface changes, this will reinitialize
275 // the picture buffer manager with the new surface. This function reads and 215 // the picture buffer manager with the new surface. This function reads and
276 // clears the surface id from |pending_surface_id_|. It will issue a decode 216 // clears the surface id from |pending_surface_id_|. It will issue a decode
277 // error if the surface change fails. Returns false on failure. 217 // error if the surface change fails. Returns false on failure.
278 bool UpdateSurface(); 218 bool UpdateSurface();
279 219
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
374 // Indicates if ResetCodecState() should be called upon the next call to 314 // Indicates if ResetCodecState() should be called upon the next call to
375 // Decode(). Allows us to avoid trashing the last few frames of a playback 315 // Decode(). Allows us to avoid trashing the last few frames of a playback
376 // when the EOS buffer is received. 316 // when the EOS buffer is received.
377 bool codec_needs_reset_; 317 bool codec_needs_reset_;
378 318
379 // True if surface creation and |picture_buffer_manager_| initialization has 319 // True if surface creation and |picture_buffer_manager_| initialization has
380 // been defered until the first Decode() call. 320 // been defered until the first Decode() call.
381 bool defer_surface_creation_; 321 bool defer_surface_creation_;
382 322
383 // Has a value if a SetSurface() call has occurred and a new surface should be 323 // Has a value if a SetSurface() call has occurred and a new surface should be
384 // switched to when possible. Cleared during OnDestroyingSurface() and if all 324 // switched to when possible. Cleared during OnSurfaceDestroyed() and if all
385 // pictures have been rendered in DequeueOutput(). 325 // pictures have been rendered in DequeueOutput().
386 base::Optional<int32_t> pending_surface_id_; 326 base::Optional<int32_t> pending_surface_id_;
387 327
388 // Copy of the VDA::Config we were given. 328 // Copy of the VDA::Config we were given.
389 Config config_; 329 Config config_;
390 330
391 OnDestroyingSurfaceCallback on_destroying_surface_cb_;
392
393 // WeakPtrFactory for posting tasks back to |this|. 331 // WeakPtrFactory for posting tasks back to |this|.
394 base::WeakPtrFactory<AndroidVideoDecodeAccelerator> weak_this_factory_; 332 base::WeakPtrFactory<AndroidVideoDecodeAccelerator> weak_this_factory_;
395 333
396 friend class AndroidVideoDecodeAcceleratorTest; 334 friend class AndroidVideoDecodeAcceleratorTest;
397 }; 335 };
398 336
399 } // namespace media 337 } // namespace media
400 338
401 #endif // MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_ 339 #endif // MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_
OLDNEW
« no previous file with comments | « media/gpu/BUILD.gn ('k') | media/gpu/android_video_decode_accelerator.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698