OLD | NEW |
---|---|
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_codec_bridge_impl.h" | 21 #include "media/base/android/media_codec_bridge_impl.h" |
22 #include "media/base/android/media_drm_bridge_cdm_context.h" | 22 #include "media/base/android/media_drm_bridge_cdm_context.h" |
23 #include "media/base/content_decryption_module.h" | 23 #include "media/base/content_decryption_module.h" |
24 #include "media/gpu/avda_codec_allocator.h" | 24 #include "media/gpu/avda_codec_allocator.h" |
25 #include "media/gpu/avda_overlay_helper.h" | |
25 #include "media/gpu/avda_picture_buffer_manager.h" | 26 #include "media/gpu/avda_picture_buffer_manager.h" |
26 #include "media/gpu/avda_state_provider.h" | 27 #include "media/gpu/avda_state_provider.h" |
27 #include "media/gpu/gpu_video_decode_accelerator_helpers.h" | 28 #include "media/gpu/gpu_video_decode_accelerator_helpers.h" |
28 #include "media/gpu/media_gpu_export.h" | 29 #include "media/gpu/media_gpu_export.h" |
29 #include "media/video/video_decode_accelerator.h" | 30 #include "media/video/video_decode_accelerator.h" |
30 #include "ui/gl/android/scoped_java_surface.h" | 31 #include "ui/gl/android/scoped_java_surface.h" |
31 #include "ui/gl/android/surface_texture.h" | 32 #include "ui/gl/android/surface_texture.h" |
32 | 33 |
33 namespace media { | 34 namespace media { |
34 class SharedMemoryRegion; | 35 class SharedMemoryRegion; |
35 | 36 |
36 // A VideoDecodeAccelerator implementation for Android. This class decodes the | 37 // A VideoDecodeAccelerator implementation for Android. This class decodes the |
37 // encded input stream using Android's MediaCodec. It handles the work of | 38 // encded input stream using Android's MediaCodec. It handles the work of |
38 // transferring data to and from MediaCodec, and delegates attaching MediaCodec | 39 // transferring data to and from MediaCodec, and delegates attaching MediaCodec |
39 // output buffers to PictureBuffers to AVDAPictureBufferManager. | 40 // output buffers to PictureBuffers to AVDAPictureBufferManager. |
40 class MEDIA_GPU_EXPORT AndroidVideoDecodeAccelerator | 41 class MEDIA_GPU_EXPORT AndroidVideoDecodeAccelerator |
41 : public VideoDecodeAccelerator, | 42 : public VideoDecodeAccelerator, |
42 public AVDAStateProvider, | 43 public AVDAStateProvider, |
43 public AVDACodecAllocatorClient { | 44 public AVDACodecAllocatorClient { |
44 public: | 45 public: |
45 static VideoDecodeAccelerator::Capabilities GetCapabilities( | 46 static VideoDecodeAccelerator::Capabilities GetCapabilities( |
46 const gpu::GpuPreferences& gpu_preferences); | 47 const gpu::GpuPreferences& gpu_preferences); |
47 | 48 |
49 // Various things that we normally ask the platform for, mostly for testing. | |
50 struct PlatformConfig { | |
51 int sdk_int = base::android::SDK_VERSION_MARSHMALLOW; | |
52 | |
53 // Is SetSurface supported? This is not the same as >= M, since we | |
54 // blacklist some devices. | |
55 bool allow_setsurface = true; | |
56 | |
57 bool force_deferred_surface_creation = false; | |
58 }; | |
59 | |
48 AndroidVideoDecodeAccelerator( | 60 AndroidVideoDecodeAccelerator( |
49 AVDACodecAllocator* codec_allocator, | 61 AVDACodecAllocator* codec_allocator, |
62 std::unique_ptr<AVDAOverlayHelper> overlay_helper, | |
50 const MakeGLContextCurrentCallback& make_context_current_cb, | 63 const MakeGLContextCurrentCallback& make_context_current_cb, |
51 const GetGLES2DecoderCallback& get_gles2_decoder_cb); | 64 const GetGLES2DecoderCallback& get_gles2_decoder_cb, |
65 const PlatformConfig* platform_config_for_test = nullptr); | |
DaleCurtis
2017/04/20 19:10:43
Only a few instances of constructions, should we j
liberato (no reviews please)
2017/04/20 22:01:38
Done.
| |
52 | 66 |
53 ~AndroidVideoDecodeAccelerator() override; | 67 ~AndroidVideoDecodeAccelerator() override; |
54 | 68 |
55 // VideoDecodeAccelerator implementation: | 69 // VideoDecodeAccelerator implementation: |
56 bool Initialize(const Config& config, Client* client) override; | 70 bool Initialize(const Config& config, Client* client) override; |
57 void Decode(const BitstreamBuffer& bitstream_buffer) override; | 71 void Decode(const BitstreamBuffer& bitstream_buffer) override; |
58 void AssignPictureBuffers(const std::vector<PictureBuffer>& buffers) override; | 72 void AssignPictureBuffers(const std::vector<PictureBuffer>& buffers) override; |
59 void ReusePictureBuffer(int32_t picture_buffer_id) override; | 73 void ReusePictureBuffer(int32_t picture_buffer_id) override; |
60 void Flush() override; | 74 void Flush() override; |
61 void Reset() override; | 75 void Reset() override; |
(...skipping 17 matching lines...) Expand all Loading... | |
79 void OnCodecConfigured( | 93 void OnCodecConfigured( |
80 std::unique_ptr<MediaCodecBridge> media_codec) override; | 94 std::unique_ptr<MediaCodecBridge> media_codec) override; |
81 | 95 |
82 private: | 96 private: |
83 friend class AVDAManager; | 97 friend class AVDAManager; |
84 | 98 |
85 // TODO(timav): evaluate the need for more states in the AVDA state machine. | 99 // TODO(timav): evaluate the need for more states in the AVDA state machine. |
86 enum State { | 100 enum State { |
87 NO_ERROR, | 101 NO_ERROR, |
88 ERROR, | 102 ERROR, |
89 // We have requested a surface, but haven't allocated it yet. When the | 103 // We haven't initialized |overlay_helper_| yet, so we don't have a surface |
90 // surface arrives, we'll transition to WAITING_FOR_CODEC, NO_ERROR, or | 104 // or a codec. After we initialize |overlay_helper_|, we'll transition to |
91 // ERROR. This is also the initial state, before we've even requested a | 105 // WAITING_FOR_CODEC, NO_ERROR, or ERROR. |
92 // surface, just because it's convenient. | 106 BEFORE_OVERLAY_INIT, |
93 WAITING_FOR_SURFACE, | |
94 // Set when we are asynchronously constructing the codec. Will transition | 107 // Set when we are asynchronously constructing the codec. Will transition |
95 // to NO_ERROR or ERROR depending on success. | 108 // to NO_ERROR or ERROR depending on success. |
96 WAITING_FOR_CODEC, | 109 WAITING_FOR_CODEC, |
97 // Set when we have a codec, but it doesn't yet have a key. | 110 // Set when we have a codec, but it doesn't yet have a key. |
98 WAITING_FOR_KEY, | 111 WAITING_FOR_KEY, |
99 // The output surface was destroyed. We must not configure a new MediaCodec | 112 // The output surface was destroyed. We must not configure a new MediaCodec |
100 // with the destroyed surface. | 113 // with the destroyed surface. |
101 SURFACE_DESTROYED, | 114 SURFACE_DESTROYED, |
102 }; | 115 }; |
103 | 116 |
104 enum DrainType { | 117 enum DrainType { |
105 DRAIN_FOR_FLUSH, | 118 DRAIN_FOR_FLUSH, |
106 DRAIN_FOR_RESET, | 119 DRAIN_FOR_RESET, |
107 DRAIN_FOR_DESTROY, | 120 DRAIN_FOR_DESTROY, |
108 }; | 121 }; |
109 | 122 |
110 // Entry point for configuring / reconfiguring a codec with a new surface. | 123 // Called once before (possibly deferred) initialization succeeds, to set up |
111 // Start surface creation by trying to allocate the surface id. Will either | 124 // |overlay_helper_| with our inital factory from VDA::Config. |
112 // InitializePictureBufferManager if the surface is available immediately, or | 125 void StartOverlayHelper(); |
113 // will wait for OnOverlayReady to do it. This will transition |state_| | |
114 // to WAITING_FOR_SURFACE or WAITING_FOR_CODEC, as needed (or NO_ERROR if it | |
115 // gets the surface and the codec without waiting). | |
116 // Note that this requires that you create a new |incoming_bundle_| with the | |
117 // appropriate surface id. | |
118 void StartSurfaceCreation(); | |
119 | 126 |
120 // Called by AndroidOverlay when a surface becomes available. | 127 // Start a transition to an overlay, or, if |!overlay|, SurfaceTexture. The |
121 void OnOverlayReady(AndroidOverlay* overlay); | 128 // transition doesn't have to be immediate; we'll favor not dropping frames. |
129 void OnTransitionToOrFromOverlay(std::unique_ptr<AndroidOverlay> overlay); | |
122 | 130 |
123 // Called by AndroidOverlay when the overlay will not call OnOverlayReady. | 131 // Called by AndroidOverlay when a surface is lost. We will discard pending |
124 void OnOverlayFailed(AndroidOverlay* overlay); | 132 // frames, as needed, to switch away from |overlay| if we're using it. Before |
125 | 133 // we return, we will have either dropped |overlay| if we own it, or posted |
126 // Called by AndroidOverlay when a surface is lost. | 134 // it for async release with the codec that's using it. We also handle the |
127 void OnSurfaceDestroyed(AndroidOverlay* overlay); | 135 // case where we're not using |overlay| at all, since that can happen too |
136 // while async codec release is pending. | |
137 void OnStopUsingOverlayImmediately(AndroidOverlay* overlay); | |
128 | 138 |
129 // Initializes the picture buffer manager to use the current surface, once | 139 // Initializes the picture buffer manager to use the current surface, once |
130 // it is available. This is not normally called directly, but rather via | 140 // it is available. This is not normally called directly, but rather via |
131 // StartSurfaceCreation. If we have a media codec already, then this will | 141 // StartSurfaceCreation. If we have a media codec already, then this will |
132 // attempt to setSurface the new surface. Otherwise, it will start codec | 142 // attempt to setSurface the new surface. Otherwise, it will start codec |
133 // config using the new surface. In that case, there might not be a codec | 143 // config using the new surface. In that case, there might not be a codec |
134 // ready even if this succeeds, but async config will be started. If | 144 // ready even if this succeeds, but async config will be started. If |
135 // setSurface fails, this will not replace the codec. On failure, this will | 145 // setSurface fails, this will not replace the codec. On failure, this will |
136 // transition |state_| to ERROR. | 146 // transition |state_| to ERROR. |
137 // Note that this assumes that there is an |incoming_bundle_| that we'll use. | 147 // Note that this assumes that there is an |incoming_bundle_| that we'll use. |
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
240 // On platforms which support seamless surface changes, this will reinitialize | 250 // On platforms which support seamless surface changes, this will reinitialize |
241 // the picture buffer manager with the new surface. This function reads and | 251 // the picture buffer manager with the new surface. This function reads and |
242 // clears the surface id from |pending_surface_id_|. It will issue a decode | 252 // clears the surface id from |pending_surface_id_|. It will issue a decode |
243 // error if the surface change fails. Returns false on failure. | 253 // error if the surface change fails. Returns false on failure. |
244 bool UpdateSurface(); | 254 bool UpdateSurface(); |
245 | 255 |
246 // Release |media_codec_| if it's not null, and notify | 256 // Release |media_codec_| if it's not null, and notify |
247 // |picture_buffer_manager_|. | 257 // |picture_buffer_manager_|. |
248 void ReleaseCodec(); | 258 void ReleaseCodec(); |
249 | 259 |
250 // Returns the surface ID from the incoming bundle, if we have one, or | 260 // ReleaseCodec(), and also drop our ref to it's surface bundle. This is the |
251 // the current surface bundle if not. The reasoning is that, if we have an | 261 // right thing to do unless you're planning to re-use the bundle with another |
252 // incoming bundle, then the current (outgoing) one has already been returned | 262 // codec. Normally, one doesn't. |
253 // to the codec allocator via DeallocateSurface. The only place this happens | 263 void ReleaseCodecAndBundle(); |
254 // is UpdateSurface, which handles it specially. | 264 |
255 int surface_id() const { | 265 base::WeakPtr<AndroidVideoDecodeAccelerator> GetWeakPtr(); |
DaleCurtis
2017/04/20 19:10:43
Again, avoid.
liberato (no reviews please)
2017/04/20 22:01:38
it has private access -- does that make it okay?.
| |
256 return incoming_bundle_ ? incoming_bundle_->surface_id | |
257 : codec_config_->surface_bundle->surface_id; | |
258 } | |
259 | 266 |
260 // Used to DCHECK that we are called on the correct thread. | 267 // Used to DCHECK that we are called on the correct thread. |
261 base::ThreadChecker thread_checker_; | 268 base::ThreadChecker thread_checker_; |
262 | 269 |
263 // To expose client callbacks from VideoDecodeAccelerator. | 270 // To expose client callbacks from VideoDecodeAccelerator. |
264 Client* client_; | 271 Client* client_; |
265 | 272 |
266 AVDACodecAllocator* codec_allocator_; | 273 AVDACodecAllocator* codec_allocator_; |
267 | 274 |
268 // Callback to set the correct gl context. | 275 // Callback to set the correct gl context. |
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
373 // Copy of the VDA::Config we were given. | 380 // Copy of the VDA::Config we were given. |
374 Config config_; | 381 Config config_; |
375 | 382 |
376 // SurfaceBundle that we're going to use for StartSurfaceCreation. This is | 383 // SurfaceBundle that we're going to use for StartSurfaceCreation. This is |
377 // separate than the bundle in |codec_config_|, since we can start surface | 384 // separate than the bundle in |codec_config_|, since we can start surface |
378 // creation while another codec is using the old surface. For example, if | 385 // creation while another codec is using the old surface. For example, if |
379 // we're going to SetSurface, then the current codec will depend on the | 386 // we're going to SetSurface, then the current codec will depend on the |
380 // current bundle until then. | 387 // current bundle until then. |
381 scoped_refptr<AVDASurfaceBundle> incoming_bundle_; | 388 scoped_refptr<AVDASurfaceBundle> incoming_bundle_; |
382 | 389 |
390 // If we have been given an overlay to use, then this is it. If we've been | |
391 // told to move to SurfaceTexture, then this will be value() == nullptr. | |
392 base::Optional<std::unique_ptr<AndroidOverlay>> incoming_overlay_; | |
393 | |
394 std::unique_ptr<AVDAOverlayHelper> overlay_helper_; | |
395 | |
396 PlatformConfig platform_config_; | |
397 | |
383 // WeakPtrFactory for posting tasks back to |this|. | 398 // WeakPtrFactory for posting tasks back to |this|. |
384 base::WeakPtrFactory<AndroidVideoDecodeAccelerator> weak_this_factory_; | 399 base::WeakPtrFactory<AndroidVideoDecodeAccelerator> weak_this_factory_; |
385 | 400 |
386 friend class AndroidVideoDecodeAcceleratorTest; | 401 friend class AndroidVideoDecodeAcceleratorTest; |
387 }; | 402 }; |
388 | 403 |
389 } // namespace media | 404 } // namespace media |
390 | 405 |
391 #endif // MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_ | 406 #endif // MEDIA_GPU_ANDROID_VIDEO_DECODE_ACCELERATOR_H_ |
OLD | NEW |