Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 // Represents the browser side of the browser <--> renderer communication | 5 // Represents the browser side of the browser <--> renderer communication |
| 6 // channel. There will be one RenderProcessHost per renderer process. | 6 // channel. There will be one RenderProcessHost per renderer process. |
| 7 | 7 |
| 8 #include "content/browser/renderer_host/render_process_host_impl.h" | 8 #include "content/browser/renderer_host/render_process_host_impl.h" |
| 9 | 9 |
| 10 #if defined(OS_WIN) | 10 #if defined(OS_WIN) |
| (...skipping 764 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 775 | 775 |
| 776 // Test if there's an unload listener. | 776 // Test if there's an unload listener. |
| 777 // NOTE: It's possible that an onunload listener may be installed | 777 // NOTE: It's possible that an onunload listener may be installed |
| 778 // while we're shutting down, so there's a small race here. Given that | 778 // while we're shutting down, so there's a small race here. Given that |
| 779 // the window is small, it's unlikely that the web page has much | 779 // the window is small, it's unlikely that the web page has much |
| 780 // state that will be lost by not calling its unload handlers properly. | 780 // state that will be lost by not calling its unload handlers properly. |
| 781 if (!SuddenTerminationAllowed()) | 781 if (!SuddenTerminationAllowed()) |
| 782 return false; | 782 return false; |
| 783 | 783 |
| 784 // Store the handle before it gets changed. | 784 // Store the handle before it gets changed. |
| 785 base::ProcessHandle handle = GetHandle(); | 785 RendererClosedDetails details(GetHandle()); |
| 786 ProcessDied(handle, base::TERMINATION_STATUS_NORMAL_TERMINATION, 0, false); | 786 DCHECK_EQ(details.status, base::TERMINATION_STATUS_NORMAL_TERMINATION); |
| 787 details.exit_code = 0; | |
|
rvargas (doing something else)
2012/03/22 22:56:59
I see... The other two values are also set on the
jar (doing other things)
2012/03/23 01:13:21
For completeness, I always like to initialize all
| |
| 788 details.was_alive = false; | |
| 789 ProcessDied(&details); | |
| 787 fast_shutdown_started_ = true; | 790 fast_shutdown_started_ = true; |
| 788 return true; | 791 return true; |
| 789 } | 792 } |
| 790 | 793 |
| 791 void RenderProcessHostImpl::DumpHandles() { | 794 void RenderProcessHostImpl::DumpHandles() { |
| 792 #if defined(OS_WIN) | 795 #if defined(OS_WIN) |
| 793 Send(new ChildProcessMsg_DumpHandles()); | 796 Send(new ChildProcessMsg_DumpHandles()); |
| 794 return; | 797 return; |
| 795 #endif | 798 #endif |
| 796 | 799 |
| (...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 940 tracked_objects::ThreadData::Status status = | 943 tracked_objects::ThreadData::Status status = |
| 941 tracked_objects::ThreadData::status(); | 944 tracked_objects::ThreadData::status(); |
| 942 Send(new ChildProcessMsg_SetProfilerStatus(status)); | 945 Send(new ChildProcessMsg_SetProfilerStatus(status)); |
| 943 } | 946 } |
| 944 | 947 |
| 945 void RenderProcessHostImpl::OnChannelError() { | 948 void RenderProcessHostImpl::OnChannelError() { |
| 946 if (!channel_.get()) | 949 if (!channel_.get()) |
| 947 return; | 950 return; |
| 948 | 951 |
| 949 // Store the handle before it gets changed. | 952 // Store the handle before it gets changed. |
| 950 base::ProcessHandle handle = GetHandle(); | 953 RendererClosedDetails details(GetHandle()); |
| 951 | |
| 952 // child_process_launcher_ can be NULL in single process mode or if fast | 954 // child_process_launcher_ can be NULL in single process mode or if fast |
| 953 // termination happened. | 955 // termination happened. |
| 954 int exit_code = 0; | 956 details.status = child_process_launcher_.get() ? |
| 955 base::TerminationStatus status = | 957 child_process_launcher_->GetChildTerminationStatus(&details.exit_code) : |
| 956 child_process_launcher_.get() ? | |
| 957 child_process_launcher_->GetChildTerminationStatus(&exit_code) : | |
| 958 base::TERMINATION_STATUS_NORMAL_TERMINATION; | 958 base::TERMINATION_STATUS_NORMAL_TERMINATION; |
| 959 | 959 |
| 960 #if defined(OS_WIN) | 960 #if defined(OS_WIN) |
| 961 if (!run_renderer_in_process()) { | 961 if (!run_renderer_in_process()) { |
| 962 if (status == base::TERMINATION_STATUS_STILL_RUNNING) { | 962 if (details.status == base::TERMINATION_STATUS_STILL_RUNNING) { |
| 963 HANDLE process = child_process_launcher_->GetHandle(); | 963 HANDLE process = child_process_launcher_->GetHandle(); |
| 964 child_process_watcher_.StartWatching( | 964 child_process_watcher_.StartWatching( |
| 965 new base::WaitableEvent(process), this); | 965 new base::WaitableEvent(process), this); |
| 966 return; | 966 return; |
| 967 } | 967 } |
| 968 } | 968 } |
| 969 #endif | 969 #endif |
| 970 ProcessDied(handle, status, exit_code, false); | 970 details.was_alive = false; |
| 971 } | 971 ProcessDied(&details); |
| 972 } | |
| 972 | 973 |
| 973 // Called when the renderer process handle has been signaled. | 974 // Called when the renderer process handle has been signaled. |
| 974 void RenderProcessHostImpl::OnWaitableEventSignaled( | 975 void RenderProcessHostImpl::OnWaitableEventSignaled( |
| 975 base::WaitableEvent* waitable_event) { | 976 base::WaitableEvent* waitable_event) { |
| 976 #if defined (OS_WIN) | 977 #if defined (OS_WIN) |
| 977 base::ProcessHandle handle = GetHandle(); | 978 RendererClosedDetails details(GetHandle()); |
| 978 int exit_code = 0; | 979 details.status = base::GetTerminationStatus(waitable_event->Release(), |
| 979 base::TerminationStatus status = | 980 &details.exit_code); |
| 980 base::GetTerminationStatus(waitable_event->Release(), &exit_code); | |
| 981 delete waitable_event; | 981 delete waitable_event; |
| 982 ProcessDied(handle, status, exit_code, true); | 982 details.was_alive = true; |
| 983 ProcessDied(&details); | |
| 983 #endif | 984 #endif |
| 984 } | 985 } |
| 985 | 986 |
| 986 content::BrowserContext* RenderProcessHostImpl::GetBrowserContext() const { | 987 content::BrowserContext* RenderProcessHostImpl::GetBrowserContext() const { |
| 987 return browser_context_; | 988 return browser_context_; |
| 988 } | 989 } |
| 989 | 990 |
| 990 int RenderProcessHostImpl::GetID() const { | 991 int RenderProcessHostImpl::GetID() const { |
| 991 return id_; | 992 return id_; |
| 992 } | 993 } |
| (...skipping 213 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1206 // Now pick a random suitable renderer, if we have any. | 1207 // Now pick a random suitable renderer, if we have any. |
| 1207 if (!suitable_renderers.empty()) { | 1208 if (!suitable_renderers.empty()) { |
| 1208 int suitable_count = static_cast<int>(suitable_renderers.size()); | 1209 int suitable_count = static_cast<int>(suitable_renderers.size()); |
| 1209 int random_index = base::RandInt(0, suitable_count - 1); | 1210 int random_index = base::RandInt(0, suitable_count - 1); |
| 1210 return suitable_renderers[random_index]; | 1211 return suitable_renderers[random_index]; |
| 1211 } | 1212 } |
| 1212 | 1213 |
| 1213 return NULL; | 1214 return NULL; |
| 1214 } | 1215 } |
| 1215 | 1216 |
| 1216 void RenderProcessHostImpl::ProcessDied(base::ProcessHandle handle, | 1217 void RenderProcessHostImpl::ProcessDied(RendererClosedDetails* details) { |
| 1217 base::TerminationStatus status, | |
| 1218 int exit_code, | |
| 1219 bool was_alive) { | |
| 1220 // Our child process has died. If we didn't expect it, it's a crash. | 1218 // Our child process has died. If we didn't expect it, it's a crash. |
| 1221 // In any case, we need to let everyone know it's gone. | 1219 // In any case, we need to let everyone know it's gone. |
| 1222 // The OnChannelError notification can fire multiple times due to nested sync | 1220 // The OnChannelError notification can fire multiple times due to nested sync |
| 1223 // calls to a renderer. If we don't have a valid channel here it means we | 1221 // calls to a renderer. If we don't have a valid channel here it means we |
| 1224 // already handled the error. | 1222 // already handled the error. |
| 1225 | 1223 |
| 1226 RendererClosedDetails details(handle, status, exit_code, was_alive); | |
| 1227 content::NotificationService::current()->Notify( | 1224 content::NotificationService::current()->Notify( |
| 1228 content::NOTIFICATION_RENDERER_PROCESS_CLOSED, | 1225 content::NOTIFICATION_RENDERER_PROCESS_CLOSED, |
| 1229 content::Source<RenderProcessHost>(this), | 1226 content::Source<RenderProcessHost>(this), |
| 1230 content::Details<RendererClosedDetails>(&details)); | 1227 content::Details<RendererClosedDetails>(details)); |
| 1231 | 1228 |
| 1232 child_process_launcher_.reset(); | 1229 child_process_launcher_.reset(); |
| 1233 channel_.reset(); | 1230 channel_.reset(); |
| 1234 gpu_message_filter_ = NULL; | 1231 gpu_message_filter_ = NULL; |
| 1235 | 1232 |
| 1236 IDMap<RenderWidgetHost>::iterator iter(&render_widget_hosts_); | 1233 IDMap<RenderWidgetHost>::iterator iter(&render_widget_hosts_); |
| 1237 while (!iter.IsAtEnd()) { | 1234 while (!iter.IsAtEnd()) { |
| 1238 RenderWidgetHostImpl::From(iter.GetCurrentValue())->OnMessageReceived( | 1235 RenderWidgetHostImpl::From(iter.GetCurrentValue())->OnMessageReceived( |
| 1239 ViewHostMsg_RenderViewGone(iter.GetCurrentKey(), | 1236 ViewHostMsg_RenderViewGone(iter.GetCurrentKey(), |
| 1240 static_cast<int>(status), | 1237 static_cast<int>(details->status), |
| 1241 exit_code)); | 1238 details->exit_code)); |
| 1242 iter.Advance(); | 1239 iter.Advance(); |
| 1243 } | 1240 } |
| 1244 | 1241 |
| 1245 ClearTransportDIBCache(); | 1242 ClearTransportDIBCache(); |
| 1246 | 1243 |
| 1247 // this object is not deleted at this point and may be reused later. | 1244 // this object is not deleted at this point and may be reused later. |
| 1248 // TODO(darin): clean this up | 1245 // TODO(darin): clean this up |
| 1249 } | 1246 } |
| 1250 | 1247 |
| 1251 void RenderProcessHostImpl::OnShutdownRequest() { | 1248 void RenderProcessHostImpl::OnShutdownRequest() { |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1336 void RenderProcessHostImpl::OnRevealFolderInOS(const FilePath& path) { | 1333 void RenderProcessHostImpl::OnRevealFolderInOS(const FilePath& path) { |
| 1337 // Only honor the request if appropriate persmissions are granted. | 1334 // Only honor the request if appropriate persmissions are granted. |
| 1338 if (ChildProcessSecurityPolicyImpl::GetInstance()->CanReadFile(GetID(), | 1335 if (ChildProcessSecurityPolicyImpl::GetInstance()->CanReadFile(GetID(), |
| 1339 path)) | 1336 path)) |
| 1340 content::GetContentClient()->browser()->OpenItem(path); | 1337 content::GetContentClient()->browser()->OpenItem(path); |
| 1341 } | 1338 } |
| 1342 | 1339 |
| 1343 void RenderProcessHostImpl::OnSavedPageAsMHTML(int job_id, int64 data_size) { | 1340 void RenderProcessHostImpl::OnSavedPageAsMHTML(int job_id, int64 data_size) { |
| 1344 MHTMLGenerationManager::GetInstance()->MHTMLGenerated(job_id, data_size); | 1341 MHTMLGenerationManager::GetInstance()->MHTMLGenerated(job_id, data_size); |
| 1345 } | 1342 } |
| OLD | NEW |