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

Side by Side Diff: content/browser/renderer_host/render_process_host_browsertest.cc

Issue 2929113002: Enable spare RenderProcessHost to be preinitialized. (Closed)
Patch Set: Change creation of storage partition to not break unittests with subtle threading issues Created 3 years, 5 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 unified diff | Download patch
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 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 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 #include "base/bind.h" 5 #include "base/bind.h"
6 #include "base/command_line.h" 6 #include "base/command_line.h"
7 #include "base/run_loop.h" 7 #include "base/run_loop.h"
8 #include "build/build_config.h" 8 #include "build/build_config.h"
9 #include "content/browser/renderer_host/render_process_host_impl.h" 9 #include "content/browser/renderer_host/render_process_host_impl.h"
10 #include "content/common/child_process_messages.h" 10 #include "content/common/child_process_messages.h"
11 #include "content/public/browser/render_frame_host.h" 11 #include "content/public/browser/render_frame_host.h"
12 #include "content/public/browser/render_process_host.h" 12 #include "content/public/browser/render_process_host.h"
13 #include "content/public/browser/render_process_host_observer.h" 13 #include "content/public/browser/render_process_host_observer.h"
14 #include "content/public/browser/web_contents.h" 14 #include "content/public/browser/web_contents.h"
15 #include "content/public/common/url_constants.h" 15 #include "content/public/common/url_constants.h"
16 #include "content/public/test/content_browser_test.h" 16 #include "content/public/test/content_browser_test.h"
17 #include "content/public/test/content_browser_test_utils.h" 17 #include "content/public/test/content_browser_test_utils.h"
18 #include "content/public/test/test_service.mojom.h" 18 #include "content/public/test/test_service.mojom.h"
19 #include "content/shell/browser/shell.h" 19 #include "content/shell/browser/shell.h"
20 #include "content/shell/browser/shell_browser_context.h"
21 #include "content/shell/browser/shell_browser_main_parts.h"
22 #include "content/shell/browser/shell_content_browser_client.h"
23 #include "content/test/test_content_browser_client.h"
20 #include "media/base/bind_to_current_loop.h" 24 #include "media/base/bind_to_current_loop.h"
21 #include "media/base/media_switches.h" 25 #include "media/base/media_switches.h"
22 #include "media/base/test_data_util.h" 26 #include "media/base/test_data_util.h"
23 #include "media/mojo/features.h" 27 #include "media/mojo/features.h"
24 #include "net/test/embedded_test_server/embedded_test_server.h" 28 #include "net/test/embedded_test_server/embedded_test_server.h"
25 29
26 #if defined(OS_WIN) 30 #if defined(OS_WIN)
27 #include "base/win/windows_version.h" 31 #include "base/win/windows_version.h"
28 #endif 32 #endif
29 33
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
66 } 70 }
67 void RenderProcessHostDestroyed(RenderProcessHost* host) override { 71 void RenderProcessHostDestroyed(RenderProcessHost* host) override {
68 ++host_destructions_; 72 ++host_destructions_;
69 } 73 }
70 74
71 int process_exits_; 75 int process_exits_;
72 int host_destructions_; 76 int host_destructions_;
73 base::Closure process_exit_callback_; 77 base::Closure process_exit_callback_;
74 }; 78 };
75 79
80 // A mock ContentBrowserClient that only considers a spare renderer to be a
81 // suitable host.
82 class SpareRendererContentBrowserClient : public TestContentBrowserClient {
83 public:
84 bool IsSuitableHost(RenderProcessHost* process_host,
85 const GURL& site_url) override {
86 if (RenderProcessHostImpl::GetSpareRenderProcessHostForTesting()) {
87 return process_host ==
88 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting();
89 }
90 return true;
91 }
92 };
93
94 // A mock ContentBrowserClient that only considers a non-spare renderer to be a
95 // suitable host, but otherwise tries to reuse processes.
96 class NonSpareRendererContentBrowserClient : public TestContentBrowserClient {
97 public:
98 bool IsSuitableHost(RenderProcessHost* process_host,
99 const GURL& site_url) override {
100 return RenderProcessHostImpl::GetSpareRenderProcessHostForTesting() !=
101 process_host;
102 }
103
104 bool ShouldTryToUseExistingProcessHost(BrowserContext* context,
105 const GURL& url) override {
106 return true;
107 }
108 };
109
76 // Sometimes the renderer process's ShutdownRequest (corresponding to the 110 // Sometimes the renderer process's ShutdownRequest (corresponding to the
77 // ViewMsg_WasSwappedOut from a previous navigation) doesn't arrive until after 111 // ViewMsg_WasSwappedOut from a previous navigation) doesn't arrive until after
78 // the browser process decides to re-use the renderer for a new purpose. This 112 // the browser process decides to re-use the renderer for a new purpose. This
79 // test makes sure the browser doesn't let the renderer die in that case. See 113 // test makes sure the browser doesn't let the renderer die in that case. See
80 // http://crbug.com/87176. 114 // http://crbug.com/87176.
81 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest, 115 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest,
82 ShutdownRequestFromActiveTabIgnored) { 116 ShutdownRequestFromActiveTabIgnored) {
83 ASSERT_TRUE(embedded_test_server()->Start()); 117 ASSERT_TRUE(embedded_test_server()->Start());
84 118
85 GURL test_url = embedded_test_server()->GetURL("/simple_page.html"); 119 GURL test_url = embedded_test_server()->GetURL("/simple_page.html");
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
123 GURL::Replacements replace_host; 157 GURL::Replacements replace_host;
124 replace_host.SetHostStr("localhost"); 158 replace_host.SetHostStr("localhost");
125 GURL another_url = embedded_test_server()->GetURL("/simple_page.html"); 159 GURL another_url = embedded_test_server()->GetURL("/simple_page.html");
126 another_url = another_url.ReplaceComponents(replace_host); 160 another_url = another_url.ReplaceComponents(replace_host);
127 NavigateToURL(CreateBrowser(), another_url); 161 NavigateToURL(CreateBrowser(), another_url);
128 162
129 // Expect that we got another process (the guest renderer was not reused). 163 // Expect that we got another process (the guest renderer was not reused).
130 EXPECT_EQ(2, RenderProcessHostCount()); 164 EXPECT_EQ(2, RenderProcessHostCount());
131 } 165 }
132 166
167 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest, SpareRenderProcessHostTaken) {
168 ASSERT_TRUE(embedded_test_server()->Start());
169
170 RenderProcessHost::WarmupSpareRenderProcessHost(
171 ShellContentBrowserClient::Get()->browser_context());
172 RenderProcessHost* spare_renderer =
173 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting();
174 EXPECT_NE(nullptr, spare_renderer);
175
176 GURL test_url = embedded_test_server()->GetURL("/simple_page.html");
177 Shell* window = CreateBrowser();
178 NavigateToURL(window, test_url);
179
180 EXPECT_EQ(spare_renderer,
181 window->web_contents()->GetMainFrame()->GetProcess());
182
183 // The spare render process host should no longer be available.
184 EXPECT_EQ(nullptr,
185 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting());
186 }
187
188 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest, SpareRenderProcessHostNotTaken) {
189 ASSERT_TRUE(embedded_test_server()->Start());
190
191 RenderProcessHost::WarmupSpareRenderProcessHost(
192 ShellContentBrowserClient::Get()->off_the_record_browser_context());
193 RenderProcessHost* spare_renderer =
194 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting();
195 GURL test_url = embedded_test_server()->GetURL("/simple_page.html");
196 Shell* window = CreateBrowser();
197 NavigateToURL(window, test_url);
198
199 // There should have been another process created for the navigation.
200 EXPECT_NE(spare_renderer,
201 window->web_contents()->GetMainFrame()->GetProcess());
202
203 // The spare RenderProcessHost should have been cleaned up. Note this
204 // behavior is identical to what would have happened if the RenderProcessHost
205 // were taken.
206 EXPECT_EQ(nullptr,
207 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting());
208 }
209
210 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest, SpareRenderProcessHostKilled) {
211 RenderProcessHost::WarmupSpareRenderProcessHost(
212 ShellContentBrowserClient::Get()->browser_context());
213
214 RenderProcessHost* spare_renderer =
215 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting();
216 mojom::TestServicePtr service;
217 ASSERT_NE(nullptr, spare_renderer);
218 BindInterface(spare_renderer, &service);
219
220 base::RunLoop run_loop;
221 set_process_exit_callback(run_loop.QuitClosure());
222 spare_renderer->AddObserver(this); // For process_exit_callback.
223
224 // Should reply with a bad message and cause process death.
225 service->DoSomething(base::Bind(&base::DoNothing));
226 run_loop.Run();
227
228 // The spare RenderProcessHost should disappear when its process dies.
229 EXPECT_EQ(nullptr,
230 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting());
231 }
232
233 // Test that the spare renderer works correctly when the limit on the maximum
234 // number of processes is small.
235 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest,
236 SpareRendererSurpressedMaxProcesses) {
237 ASSERT_TRUE(embedded_test_server()->Start());
238
239 SpareRendererContentBrowserClient browser_client;
240 ContentBrowserClient* old_client =
241 SetBrowserClientForTesting(&browser_client);
242
243 RenderProcessHost::SetMaxRendererProcessCount(1);
244
245 // A process is created with shell startup, so with a maximum of one renderer
246 // process the spare RPH should not be created.
247 RenderProcessHost::WarmupSpareRenderProcessHost(
248 ShellContentBrowserClient::Get()->browser_context());
249 EXPECT_EQ(nullptr,
250 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting());
251
252 // A spare RPH should be created with a max of 2 renderer processes.
253 RenderProcessHost::SetMaxRendererProcessCount(2);
254 RenderProcessHost::WarmupSpareRenderProcessHost(
255 ShellContentBrowserClient::Get()->browser_context());
256 RenderProcessHost* spare_renderer =
257 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting();
258 EXPECT_NE(nullptr, spare_renderer);
259
260 // Thanks to the injected SpareRendererContentBrowserClient and the limit on
261 // processes, the spare RPH will always be used via GetExistingProcessHost()
262 // rather than picked up via MaybeTakeSpareRenderProcessHost().
263 GURL test_url = embedded_test_server()->GetURL("/simple_page.html");
264 Shell* new_window = CreateBrowser();
265 NavigateToURL(new_window, test_url);
266 // The spare RPH should have been dropped during CreateBrowser() and given to
267 // the new window.
268 EXPECT_EQ(nullptr,
269 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting());
270 EXPECT_EQ(spare_renderer,
271 new_window->web_contents()->GetMainFrame()->GetProcess());
272
273 // Revert to the default process limit and original ContentBrowserClient.
274 RenderProcessHost::SetMaxRendererProcessCount(0);
275 SetBrowserClientForTesting(old_client);
276 }
277
278 // Check that the spare renderer is dropped if an existing process is reused.
279 IN_PROC_BROWSER_TEST_F(RenderProcessHostTest, SpareRendererOnProcessReuse) {
280 ASSERT_TRUE(embedded_test_server()->Start());
281
282 NonSpareRendererContentBrowserClient browser_client;
283 ContentBrowserClient* old_client =
284 SetBrowserClientForTesting(&browser_client);
285
286 RenderProcessHost::WarmupSpareRenderProcessHost(
287 ShellContentBrowserClient::Get()->browser_context());
288 RenderProcessHost* spare_renderer =
289 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting();
290 EXPECT_NE(nullptr, spare_renderer);
291
292 // This should resuse the existing process and cause the spare renderer to be
293 // dropped.
294 Shell* new_browser = CreateBrowser();
295 EXPECT_EQ(shell()->web_contents()->GetMainFrame()->GetProcess(),
296 new_browser->web_contents()->GetMainFrame()->GetProcess());
297 EXPECT_NE(spare_renderer,
298 new_browser->web_contents()->GetMainFrame()->GetProcess());
299 EXPECT_EQ(nullptr,
300 RenderProcessHostImpl::GetSpareRenderProcessHostForTesting());
301
302 SetBrowserClientForTesting(old_client);
303 }
304
133 class ShellCloser : public RenderProcessHostObserver { 305 class ShellCloser : public RenderProcessHostObserver {
134 public: 306 public:
135 ShellCloser(Shell* shell, std::string* logging_string) 307 ShellCloser(Shell* shell, std::string* logging_string)
136 : shell_(shell), logging_string_(logging_string) {} 308 : shell_(shell), logging_string_(logging_string) {}
137 309
138 protected: 310 protected:
139 // RenderProcessHostObserver: 311 // RenderProcessHostObserver:
140 void RenderProcessExited(RenderProcessHost* host, 312 void RenderProcessExited(RenderProcessHost* host,
141 base::TerminationStatus status, 313 base::TerminationStatus status,
142 int exit_code) override { 314 int exit_code) override {
(...skipping 179 matching lines...) Expand 10 before | Expand all | Expand 10 after
322 // Verify shutdown went as expected. 494 // Verify shutdown went as expected.
323 EXPECT_EQ(0, rph->get_audio_stream_count_for_testing()); 495 EXPECT_EQ(0, rph->get_audio_stream_count_for_testing());
324 EXPECT_EQ(1, process_exits_); 496 EXPECT_EQ(1, process_exits_);
325 EXPECT_EQ(0, host_destructions_); 497 EXPECT_EQ(0, host_destructions_);
326 if (!host_destructions_) 498 if (!host_destructions_)
327 rph->RemoveObserver(this); 499 rph->RemoveObserver(this);
328 } 500 }
329 501
330 } // namespace 502 } // namespace
331 } // namespace content 503 } // namespace content
OLDNEW
« no previous file with comments | « content/browser/frame_host/render_frame_host_manager.cc ('k') | content/browser/renderer_host/render_process_host_impl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698