IndexedDBFactory now ForceCloses databases.
[chromium-blink-merge.git] / content / browser / android / in_process / synchronous_compositor_factory_impl.cc
blob5fc68f364a38498c5a7139d3ae11839fe8ccdb45
1 // Copyright 2014 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.
5 #include "content/browser/android/in_process/synchronous_compositor_factory_impl.h"
7 #include "content/browser/android/in_process/synchronous_compositor_output_surface.h"
8 #include "content/public/browser/browser_thread.h"
9 #include "gpu/command_buffer/client/gl_in_process_context.h"
10 #include "ui/gl/android/surface_texture.h"
11 #include "ui/gl/gl_surface.h"
12 #include "webkit/common/gpu/context_provider_in_process.h"
13 #include "webkit/common/gpu/webgraphicscontext3d_in_process_command_buffer_impl.h"
15 namespace content {
17 namespace {
19 class VideoContextProvider
20 : public StreamTextureFactorySynchronousImpl::ContextProvider {
21 public:
22 VideoContextProvider(
23 const scoped_refptr<cc::ContextProvider>& context_provider,
24 gpu::GLInProcessContext* gl_in_process_context)
25 : context_provider_(context_provider),
26 gl_in_process_context_(gl_in_process_context) {}
28 virtual scoped_refptr<gfx::SurfaceTexture> GetSurfaceTexture(
29 uint32 stream_id) OVERRIDE {
30 return gl_in_process_context_->GetSurfaceTexture(stream_id);
33 virtual blink::WebGraphicsContext3D* Context3d() OVERRIDE {
34 return context_provider_->Context3d();
37 private:
38 friend class base::RefCountedThreadSafe<VideoContextProvider>;
39 virtual ~VideoContextProvider() {}
41 scoped_refptr<cc::ContextProvider> context_provider_;
42 gpu::GLInProcessContext* gl_in_process_context_;
44 DISALLOW_COPY_AND_ASSIGN(VideoContextProvider);
47 } // namespace
49 using webkit::gpu::WebGraphicsContext3DInProcessCommandBufferImpl;
51 SynchronousCompositorFactoryImpl::SynchronousCompositorFactoryImpl()
52 : wrapped_gl_context_for_main_thread_(NULL),
53 num_hardware_compositors_(0) {
54 SynchronousCompositorFactory::SetInstance(this);
57 SynchronousCompositorFactoryImpl::~SynchronousCompositorFactoryImpl() {}
59 scoped_refptr<base::MessageLoopProxy>
60 SynchronousCompositorFactoryImpl::GetCompositorMessageLoop() {
61 return BrowserThread::GetMessageLoopProxyForThread(BrowserThread::UI);
64 scoped_ptr<cc::OutputSurface>
65 SynchronousCompositorFactoryImpl::CreateOutputSurface(int routing_id) {
66 scoped_ptr<SynchronousCompositorOutputSurface> output_surface(
67 new SynchronousCompositorOutputSurface(routing_id));
68 return output_surface.PassAs<cc::OutputSurface>();
71 InputHandlerManagerClient*
72 SynchronousCompositorFactoryImpl::GetInputHandlerManagerClient() {
73 return synchronous_input_event_filter();
76 scoped_refptr<cc::ContextProvider>
77 SynchronousCompositorFactoryImpl::GetOffscreenContextProviderForMainThread() {
78 // This check only guarantees the main thread context is created after
79 // a compositor did successfully initialize hardware draw in the past.
80 // In particular this does not guarantee that the main thread context
81 // will fail creation when all compositors release hardware draw.
82 bool failed = !CanCreateMainThreadContext();
83 if (!failed &&
84 (!offscreen_context_for_main_thread_.get() ||
85 offscreen_context_for_main_thread_->DestroyedOnMainThread())) {
86 offscreen_context_for_main_thread_ =
87 webkit::gpu::ContextProviderInProcess::Create(
88 CreateOffscreenContext(),
89 "Compositor-Offscreen");
90 failed = !offscreen_context_for_main_thread_.get() ||
91 !offscreen_context_for_main_thread_->BindToCurrentThread();
94 if (failed) {
95 offscreen_context_for_main_thread_ = NULL;
96 wrapped_gl_context_for_main_thread_ = NULL;
98 return offscreen_context_for_main_thread_;
101 // This is called on both renderer main thread (offscreen context creation
102 // path shared between cross-process and in-process platforms) and renderer
103 // compositor impl thread (InitializeHwDraw) in order to support Android
104 // WebView synchronously enable and disable hardware mode multiple times in
105 // the same task. This is ok because in-process WGC3D creation may happen on
106 // any thread and is lightweight.
107 scoped_refptr<cc::ContextProvider> SynchronousCompositorFactoryImpl::
108 GetOffscreenContextProviderForCompositorThread() {
109 base::AutoLock lock(offscreen_context_for_compositor_thread_lock_);
110 if (!offscreen_context_for_compositor_thread_.get() ||
111 offscreen_context_for_compositor_thread_->DestroyedOnMainThread()) {
112 offscreen_context_for_compositor_thread_ =
113 webkit::gpu::ContextProviderInProcess::CreateOffscreen();
115 return offscreen_context_for_compositor_thread_;
118 scoped_ptr<StreamTextureFactory>
119 SynchronousCompositorFactoryImpl::CreateStreamTextureFactory(int view_id) {
120 scoped_ptr<StreamTextureFactorySynchronousImpl> factory(
121 new StreamTextureFactorySynchronousImpl(
122 base::Bind(&SynchronousCompositorFactoryImpl::
123 TryCreateStreamTextureFactory,
124 base::Unretained(this)),
125 view_id));
126 return factory.PassAs<StreamTextureFactory>();
129 void SynchronousCompositorFactoryImpl::CompositorInitializedHardwareDraw() {
130 base::AutoLock lock(num_hardware_compositor_lock_);
131 num_hardware_compositors_++;
134 void SynchronousCompositorFactoryImpl::CompositorReleasedHardwareDraw() {
135 bool should_release_resources = false;
137 base::AutoLock lock(num_hardware_compositor_lock_);
138 DCHECK_GT(num_hardware_compositors_, 0u);
139 num_hardware_compositors_--;
140 should_release_resources = num_hardware_compositors_ == 0u;
142 if (should_release_resources)
143 ReleaseGlobalHardwareResources();
146 void SynchronousCompositorFactoryImpl::ReleaseGlobalHardwareResources() {
148 base::AutoLock lock(offscreen_context_for_compositor_thread_lock_);
149 offscreen_context_for_compositor_thread_ = NULL;
152 // TODO(boliu): Properly clean up command buffer server of main thread
153 // context here.
156 bool SynchronousCompositorFactoryImpl::CanCreateMainThreadContext() {
157 base::AutoLock lock(num_hardware_compositor_lock_);
158 return num_hardware_compositors_ > 0;
161 scoped_refptr<StreamTextureFactorySynchronousImpl::ContextProvider>
162 SynchronousCompositorFactoryImpl::TryCreateStreamTextureFactory() {
163 scoped_refptr<StreamTextureFactorySynchronousImpl::ContextProvider>
164 context_provider;
165 if (CanCreateMainThreadContext() &&
166 GetOffscreenContextProviderForMainThread()) {
167 DCHECK(offscreen_context_for_main_thread_);
168 DCHECK(wrapped_gl_context_for_main_thread_);
169 context_provider =
170 new VideoContextProvider(offscreen_context_for_main_thread_,
171 wrapped_gl_context_for_main_thread_);
173 return context_provider;
176 // TODO(boliu): Deduplicate this with synchronous_compositor_output_surface.cc.
177 scoped_ptr<WebGraphicsContext3DInProcessCommandBufferImpl>
178 SynchronousCompositorFactoryImpl::CreateOffscreenContext() {
179 if (!gfx::GLSurface::InitializeOneOff())
180 return scoped_ptr<WebGraphicsContext3DInProcessCommandBufferImpl>();
182 const gfx::GpuPreference gpu_preference = gfx::PreferDiscreteGpu;
184 blink::WebGraphicsContext3D::Attributes attributes;
185 attributes.antialias = false;
186 attributes.shareResources = true;
187 attributes.noAutomaticFlushes = true;
189 gpu::GLInProcessContextAttribs in_process_attribs;
190 WebGraphicsContext3DInProcessCommandBufferImpl::ConvertAttributes(
191 attributes, &in_process_attribs);
192 scoped_ptr<gpu::GLInProcessContext> context(
193 gpu::GLInProcessContext::CreateContext(true,
194 NULL,
195 gfx::Size(1, 1),
196 attributes.shareResources,
197 in_process_attribs,
198 gpu_preference));
200 wrapped_gl_context_for_main_thread_ = context.get();
201 if (!context.get())
202 return scoped_ptr<WebGraphicsContext3DInProcessCommandBufferImpl>();
204 return scoped_ptr<WebGraphicsContext3DInProcessCommandBufferImpl>(
205 WebGraphicsContext3DInProcessCommandBufferImpl::WrapContext(
206 context.Pass(), attributes));
209 } // namespace content