ca2ccf9ee0510b4fb0d1c5478784f78c0465d731
[platform/framework/web/crosswalk.git] / src / content / browser / gpu / gpu_ipc_browsertests.cc
1 // Copyright 2013 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 #include "base/command_line.h"
6 #include "base/run_loop.h"
7 #include "content/browser/gpu/browser_gpu_channel_host_factory.h"
8 #include "content/browser/gpu/gpu_process_host_ui_shim.h"
9 #include "content/common/gpu/client/context_provider_command_buffer.h"
10 #include "content/common/gpu/client/webgraphicscontext3d_command_buffer_impl.h"
11 #include "content/common/gpu/gpu_process_launch_causes.h"
12 #include "content/public/browser/browser_thread.h"
13 #include "content/public/browser/gpu_data_manager.h"
14 #include "content/public/common/content_switches.h"
15 #include "content/test/content_browser_test.h"
16 #include "ui/gl/gl_switches.h"
17 #include "webkit/common/gpu/webgraphicscontext3d_in_process_command_buffer_impl.h"
18
19 namespace {
20
21 using content::WebGraphicsContext3DCommandBufferImpl;
22
23 class ContextTestBase : public content::ContentBrowserTest {
24  public:
25   virtual void SetUpOnMainThread() OVERRIDE {
26     if (!content::BrowserGpuChannelHostFactory::CanUseForTesting())
27       return;
28
29     if (!content::BrowserGpuChannelHostFactory::instance())
30       content::BrowserGpuChannelHostFactory::Initialize(true);
31
32     content::BrowserGpuChannelHostFactory* factory =
33         content::BrowserGpuChannelHostFactory::instance();
34     CHECK(factory);
35     scoped_refptr<content::GpuChannelHost> gpu_channel_host(
36         factory->EstablishGpuChannelSync(
37             content::
38                 CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE));
39     context_.reset(
40         WebGraphicsContext3DCommandBufferImpl::CreateOffscreenContext(
41             gpu_channel_host.get(),
42             blink::WebGraphicsContext3D::Attributes(),
43             GURL(),
44             WebGraphicsContext3DCommandBufferImpl::SharedMemoryLimits()));
45     CHECK(context_.get());
46     context_->makeContextCurrent();
47     context_support_ = context_->GetContextSupport();
48     ContentBrowserTest::SetUpOnMainThread();
49   }
50
51   virtual void TearDownOnMainThread() OVERRIDE {
52     // Must delete the context first.
53     context_.reset(NULL);
54     ContentBrowserTest::TearDownOnMainThread();
55   }
56
57  protected:
58   scoped_ptr<WebGraphicsContext3DCommandBufferImpl> context_;
59   gpu::ContextSupport* context_support_;
60 };
61
62 }  // namespace
63
64 // Include the shared tests.
65 #define CONTEXT_TEST_F IN_PROC_BROWSER_TEST_F
66 #include "content/common/gpu/client/gpu_context_tests.h"
67
68 namespace content {
69
70 class BrowserGpuChannelHostFactoryTest : public ContextTestBase {
71  public:
72   virtual void SetUpOnMainThread() OVERRIDE {
73     if (!content::BrowserGpuChannelHostFactory::CanUseForTesting())
74       return;
75
76     // Start all tests without a gpu channel so that the tests exercise a
77     // consistent codepath.
78     if (!content::BrowserGpuChannelHostFactory::instance())
79       content::BrowserGpuChannelHostFactory::Initialize(false);
80
81     CHECK(GetFactory());
82
83     ContentBrowserTest::SetUpOnMainThread();
84   }
85
86   virtual void TearDownOnMainThread() OVERRIDE {
87     ContextTestBase::TearDownOnMainThread();
88   }
89
90   virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE {
91     // Start all tests without a gpu channel so that the tests exercise a
92     // consistent codepath.
93     command_line->AppendSwitch(switches::kDisableGpuProcessPrelaunch);
94   }
95
96   void OnContextLost(const base::Closure callback, int* counter) {
97     (*counter)++;
98     callback.Run();
99   }
100
101  protected:
102   BrowserGpuChannelHostFactory* GetFactory() {
103     return BrowserGpuChannelHostFactory::instance();
104   }
105
106   bool IsChannelEstablished() {
107     return GetFactory()->GetGpuChannel() != NULL;
108   }
109
110   void EstablishAndWait() {
111     base::RunLoop run_loop;
112     GetFactory()->EstablishGpuChannel(
113         CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE,
114         run_loop.QuitClosure());
115     run_loop.Run();
116   }
117
118   GpuChannelHost* GetGpuChannel() {
119     return GetFactory()->GetGpuChannel();
120   }
121
122   static void Signal(bool *event) {
123     CHECK_EQ(*event, false);
124     *event = true;
125   }
126
127   scoped_ptr<WebGraphicsContext3DCommandBufferImpl> CreateContext() {
128     return make_scoped_ptr(
129         WebGraphicsContext3DCommandBufferImpl::CreateOffscreenContext(
130             GetGpuChannel(),
131             blink::WebGraphicsContext3D::Attributes(),
132             GURL(),
133             WebGraphicsContext3DCommandBufferImpl::SharedMemoryLimits()));
134   }
135 };
136
137 IN_PROC_BROWSER_TEST_F(BrowserGpuChannelHostFactoryTest, Basic) {
138   if (!context_)
139     return;
140
141   DCHECK(!IsChannelEstablished());
142   EstablishAndWait();
143   EXPECT_TRUE(GetGpuChannel() != NULL);
144 }
145
146 IN_PROC_BROWSER_TEST_F(BrowserGpuChannelHostFactoryTest,
147                        EstablishAndTerminate) {
148   if (!context_)
149     return;
150
151   DCHECK(!IsChannelEstablished());
152   base::RunLoop run_loop;
153   GetFactory()->EstablishGpuChannel(
154       CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE,
155       run_loop.QuitClosure());
156   GetFactory()->Terminate();
157
158   // The callback should still trigger.
159   run_loop.Run();
160 }
161
162 IN_PROC_BROWSER_TEST_F(BrowserGpuChannelHostFactoryTest, AlreadyEstablished) {
163   if (!context_)
164     return;
165
166   DCHECK(!IsChannelEstablished());
167   scoped_refptr<GpuChannelHost> gpu_channel =
168       GetFactory()->EstablishGpuChannelSync(
169           CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE);
170
171   // Expect established callback immediately.
172   bool event = false;
173   GetFactory()->EstablishGpuChannel(
174       CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE,
175       base::Bind(&BrowserGpuChannelHostFactoryTest::Signal, &event));
176   EXPECT_TRUE(event);
177   EXPECT_EQ(gpu_channel, GetGpuChannel());
178 }
179
180 IN_PROC_BROWSER_TEST_F(BrowserGpuChannelHostFactoryTest, CrashAndRecover) {
181   if (!context_)
182     return;
183
184   DCHECK(!IsChannelEstablished());
185   EstablishAndWait();
186   scoped_refptr<GpuChannelHost> host = GetGpuChannel();
187
188   scoped_refptr<ContextProviderCommandBuffer> provider =
189       ContextProviderCommandBuffer::Create(CreateContext(),
190                                            "BrowserGpuChannelHostFactoryTest");
191   base::RunLoop run_loop;
192   int counter = 0;
193   provider->SetLostContextCallback(
194       base::Bind(&BrowserGpuChannelHostFactoryTest::OnContextLost,
195                  base::Unretained(this), run_loop.QuitClosure(), &counter));
196   EXPECT_TRUE(provider->BindToCurrentThread());
197   GpuProcessHostUIShim* shim =
198       GpuProcessHostUIShim::FromID(GetFactory()->GpuProcessHostId());
199   EXPECT_TRUE(shim != NULL);
200   shim->SimulateCrash();
201   run_loop.Run();
202
203   EXPECT_EQ(1, counter);
204   EXPECT_FALSE(IsChannelEstablished());
205   EstablishAndWait();
206   EXPECT_TRUE(IsChannelEstablished());
207 }
208
209 }  // namespace content