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

Unified Diff: content/common/gpu/media/android_video_decode_accelerator.cc

Issue 1680213002: Start using deferred rendering for WebView on L. Base URL: https://chromium.googlesource.com/chromium/src.git@measure_copy
Patch Set: cleanup Created 4 years, 10 months 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « content/common/gpu/media/android_video_decode_accelerator.h ('k') | media/filters/gpu_video_decoder.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: content/common/gpu/media/android_video_decode_accelerator.cc
diff --git a/content/common/gpu/media/android_video_decode_accelerator.cc b/content/common/gpu/media/android_video_decode_accelerator.cc
index 3942a80ff3b4b27e042912b7853cfaac8cdc1702..64653a63f3d31204021d8df068405252729ac206 100644
--- a/content/common/gpu/media/android_video_decode_accelerator.cc
+++ b/content/common/gpu/media/android_video_decode_accelerator.cc
@@ -127,15 +127,22 @@ class AndroidVideoDecodeAccelerator::OnFrameAvailableHandler
public:
// We do not retain ownership of |owner|. It must remain valid until
// after ClearOwner() is called. This will register with
- // |surface_texture| to receive OnFrameAvailable callbacks.
+ // |surface_texture| to receive OnFrameAvailable callbacks. If
+ // |use_separate_thread| is true, then we'll request that the callback happens
+ // on a thread that is dedicated to SurfaceTexture callbacks.
OnFrameAvailableHandler(
AndroidVideoDecodeAccelerator* owner,
- const scoped_refptr<gfx::SurfaceTexture>& surface_texture)
+ const scoped_refptr<gfx::SurfaceTexture>& surface_texture,
+ bool use_separate_thread)
: owner_(owner) {
// Note that the callback owns a strong ref to us.
- surface_texture->SetFrameAvailableCallbackOnAnyThread(
- base::Bind(&OnFrameAvailableHandler::OnFrameAvailable,
- scoped_refptr<OnFrameAvailableHandler>(this)));
+ base::Closure cb = base::Bind(&OnFrameAvailableHandler::OnFrameAvailable,
+ scoped_refptr<OnFrameAvailableHandler>(this));
+
+ if (use_separate_thread)
+ surface_texture->SetFrameAvailableCallbackOnSeparateThread(cb);
+ else
+ surface_texture->SetFrameAvailableCallbackOnAnyThread(cb);
}
// Forget about our owner, which is required before one deletes it.
@@ -257,7 +264,14 @@ AndroidVideoDecodeAccelerator::AndroidVideoDecodeAccelerator(
if (UseDeferredRenderingStrategy()) {
// TODO(liberato, watk): Figure out what we want to do about zero copy for
// fullscreen external SurfaceView in WebView. http://crbug.com/582170.
- DCHECK(!gl_decoder_->GetContextGroup()->mailbox_manager()->UsesSync());
+
+ // Make sure that we're making a copy in sync mode, to verify that our
+ // guess about whether we're in sync mode in NeedsBrowserCopy is correct.
+ // Also make sure that, if we're in sync mode, that we're using a threaded
+ // callback so that it doesn't deadlock with the main thread.
+ DCHECK(!gl_decoder_->GetContextGroup()->mailbox_manager()->UsesSync() ||
+ (DeferredStrategyNeedsBrowserCopy() && IsCallbackThreadable()));
+
DVLOG(1) << __FUNCTION__ << ", using deferred rendering strategy.";
strategy_.reset(new AndroidDeferredRenderingBackingStrategy(this));
} else {
@@ -335,8 +349,14 @@ bool AndroidVideoDecodeAccelerator::Initialize(const Config& config,
scoped_refptr<gfx::SurfaceTexture> surface_texture =
strategy_->GetSurfaceTexture();
if (surface_texture) {
+ // The deferred strategy requires threading the callback if we're using
+ // the sync compositor.
+ bool use_separate_thread =
+ gl_decoder_->GetContextGroup()->mailbox_manager()->UsesSync() &&
+ UseDeferredRenderingStrategy();
+ DCHECK(!use_separate_thread || IsCallbackThreadable());
on_frame_available_handler_ =
- new OnFrameAvailableHandler(this, surface_texture);
+ new OnFrameAvailableHandler(this, surface_texture, use_separate_thread);
}
// For encrypted streams we postpone configuration until MediaCrypto is
@@ -1102,10 +1122,37 @@ void AndroidVideoDecodeAccelerator::ManageTimer(bool did_work) {
// static
bool AndroidVideoDecodeAccelerator::UseDeferredRenderingStrategy() {
- const base::CommandLine* cmd_line = base::CommandLine::ForCurrentProcess();
// TODO(liberato, watk): Figure out what we want to do about zero copy for
// fullscreen external SurfaceView in WebView. http://crbug.com/582170.
- return !cmd_line->HasSwitch(switches::kEnableThreadedTextureMailboxes);
+ // If we are at API 21, we can use this any time. Otherwise, we cannot use
+ // it for webview, since we cannot set the callback thread, causing a
+ // deadlock with the compositor.
+ return IsCallbackThreadable() || !DeferredStrategyNeedsBrowserCopy();
+}
+
+// static
+bool AndroidVideoDecodeAccelerator::DeferredStrategyNeedsBrowserCopy() {
+ // If we're using the synchronous mailbox mechanism and the deferred
+ // rendering strategy, then we need to force a copy before sending to
+ // the browser compositor.
+ // The copy is required because SurfaceTexture client textures can't be
+ // shared across unrelated GL contexts. By deferring the copy until the
+ // frame is sent to the browser compositor, we can limit the number of
+ // outstanding copies to be ~2, regardless of how many the pipeline wants
+ // for better playback.
+ // In practice, all of that means "WebView requires a copy".
+
+ // We'd really like to check
+ // gl_decoder_->GetContextGroup()->mailbox_manager()->UsesSync() here, but
+ // we're called too early in start-up for that to be set properly.
+ // Instead, we use this switch and verify it later.
+ const base::CommandLine* cmd_line = base::CommandLine::ForCurrentProcess();
+ return cmd_line->HasSwitch(switches::kEnableThreadedTextureMailboxes);
+}
+
+// static
+bool AndroidVideoDecodeAccelerator::IsCallbackThreadable() {
+ return base::android::BuildInfo::GetInstance()->sdk_int() >= 21;
}
// static
@@ -1146,6 +1193,9 @@ AndroidVideoDecodeAccelerator::GetCapabilities() {
NEEDS_ALL_PICTURE_BUFFERS_TO_DECODE |
media::VideoDecodeAccelerator::Capabilities::
SUPPORTS_EXTERNAL_OUTPUT_SURFACE;
+ if (DeferredStrategyNeedsBrowserCopy())
+ capabilities.flags |=
+ media::VideoDecodeAccelerator::Capabilities::COPY_REQUIRED;
}
return capabilities;
« no previous file with comments | « content/common/gpu/media/android_video_decode_accelerator.h ('k') | media/filters/gpu_video_decoder.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698