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

Unified Diff: content/browser/renderer_host/render_process_host_impl.cc

Issue 2857213005: PlzNavigate: implement process reuse for ServiceWorkers (Closed)
Patch Set: Fixed compilation error Created 3 years, 7 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
Index: content/browser/renderer_host/render_process_host_impl.cc
diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc
index 4b8da41c0162081e2f28950e3fa15fba28df747e..0e30f25ad8c6dd539c5963fe4e5058ca2e368c28 100644
--- a/content/browser/renderer_host/render_process_host_impl.cc
+++ b/content/browser/renderer_host/render_process_host_impl.cc
@@ -629,6 +629,67 @@ class RenderProcessHostIsReadyObserver : public RenderProcessHostObserver {
DISALLOW_COPY_AND_ASSIGN(RenderProcessHostIsReadyObserver);
};
+// The following object is used to keep track of which sites
+// RenderProcessHosts are hosting frames and expecting navigations to.
+// There are two of them per BrowserContext, one for frames and one for
+// navigations.
+const void* const kCommittedSiteCountPerProcessTrackerKey =
+ "CommittedSiteCountPerProcessTrackerKey";
+const void* const kPendingSiteCountPerProcessTrackerKey =
+ "PendingSiteCountPerProcessTrackerKey";
+class SiteCountPerProcessTracker : public base::SupportsUserData::Data {
+ public:
+ SiteCountPerProcessTracker() {}
+ ~SiteCountPerProcessTracker() override {}
+
+ void AddCountForSiteForProcess(int render_process_host_id,
+ const GURL& site_url) {
+ std::map<ProcessID, Count>& counts_per_process = map_[site_url];
+ ++counts_per_process[render_process_host_id];
+ }
+
+ void RemoveCountForSiteForProcess(int render_process_host_id,
+ const GURL& site_url) {
+ auto result = map_.find(site_url);
+ DCHECK(result != map_.end());
+ std::map<ProcessID, Count>& counts_per_process = result->second;
+
+ --counts_per_process[render_process_host_id];
+ DCHECK(counts_per_process[render_process_host_id] >= 0);
+
+ if (counts_per_process[render_process_host_id] == 0)
+ counts_per_process.erase(render_process_host_id);
+
+ if (counts_per_process.empty())
+ map_.erase(site_url);
+ }
+
+ void FindRenderProcessesForSite(
+ const GURL& site_url,
+ std::set<RenderProcessHost*>* foreground_processes,
+ std::set<RenderProcessHost*>* background_processes) {
+ auto result = map_.find(site_url);
+ if (result == map_.end())
+ return;
+
+ std::map<ProcessID, Count>& counts_per_process = result->second;
+ for (auto iter : counts_per_process) {
+ RenderProcessHost* host = RenderProcessHost::FromID(iter.first);
+ DCHECK(host);
+ if (host->VisibleWidgetCount())
+ foreground_processes->insert(host);
+ else
+ background_processes->insert(host);
+ }
+ }
+
+ private:
+ using ProcessID = int;
+ using Count = int;
+ using CountPerProcessPerSiteMap = std::map<GURL, std::map<ProcessID, Count>>;
+ CountPerProcessPerSiteMap map_;
+};
+
} // namespace
RendererMainThreadFactoryFunction g_renderer_main_thread_factory = NULL;
@@ -1748,6 +1809,82 @@ void RenderProcessHostImpl::set_render_process_host_factory(
g_render_process_host_factory_ = rph_factory;
}
+// static
+void RenderProcessHostImpl::AddFrameWithSite(
+ BrowserContext* browser_context,
+ RenderProcessHost* render_process_host,
+ const GURL& site_url) {
+ if (site_url.is_empty())
+ return;
+
+ SiteCountPerProcessTracker* tracker =
+ static_cast<SiteCountPerProcessTracker*>(browser_context->GetUserData(
+ kCommittedSiteCountPerProcessTrackerKey));
+ if (!tracker) {
+ tracker = new SiteCountPerProcessTracker();
+ browser_context->SetUserData(kCommittedSiteCountPerProcessTrackerKey,
+ base::WrapUnique(tracker));
+ }
+ tracker->AddCountForSiteForProcess(render_process_host->GetID(), site_url);
+}
+
+// static
+void RenderProcessHostImpl::RemoveFrameWithSite(
+ BrowserContext* browser_context,
+ RenderProcessHost* render_process_host,
+ const GURL& site_url) {
+ if (site_url.is_empty())
+ return;
+
+ SiteCountPerProcessTracker* tracker =
+ static_cast<SiteCountPerProcessTracker*>(browser_context->GetUserData(
+ kCommittedSiteCountPerProcessTrackerKey));
+ if (!tracker) {
+ tracker = new SiteCountPerProcessTracker();
+ browser_context->SetUserData(kCommittedSiteCountPerProcessTrackerKey,
+ base::WrapUnique(tracker));
+ }
+ tracker->RemoveCountForSiteForProcess(render_process_host->GetID(), site_url);
+}
+
+// static
+void RenderProcessHostImpl::AddExpectedNavigationToSite(
+ BrowserContext* browser_context,
+ RenderProcessHost* render_process_host,
+ const GURL& site_url) {
+ if (site_url.is_empty())
+ return;
+
+ SiteCountPerProcessTracker* tracker =
+ static_cast<SiteCountPerProcessTracker*>(
+ browser_context->GetUserData(kPendingSiteCountPerProcessTrackerKey));
+ if (!tracker) {
+ tracker = new SiteCountPerProcessTracker();
+ browser_context->SetUserData(kPendingSiteCountPerProcessTrackerKey,
+ base::WrapUnique(tracker));
+ }
+ tracker->AddCountForSiteForProcess(render_process_host->GetID(), site_url);
+}
+
+// static
+void RenderProcessHostImpl::RemoveExpectedNavigationToSite(
+ BrowserContext* browser_context,
+ RenderProcessHost* render_process_host,
+ const GURL& site_url) {
+ if (site_url.is_empty())
+ return;
+
+ SiteCountPerProcessTracker* tracker =
+ static_cast<SiteCountPerProcessTracker*>(
+ browser_context->GetUserData(kPendingSiteCountPerProcessTrackerKey));
+ if (!tracker) {
+ tracker = new SiteCountPerProcessTracker();
+ browser_context->SetUserData(kPendingSiteCountPerProcessTrackerKey,
+ base::WrapUnique(tracker));
+ }
+ tracker->RemoveCountForSiteForProcess(render_process_host->GetID(), site_url);
+}
+
bool RenderProcessHostImpl::IsForGuestsOnly() const {
return is_for_guests_only_;
}
@@ -2864,6 +3001,9 @@ RenderProcessHost* RenderProcessHostImpl::GetProcessHostForSiteInstance(
DCHECK(SiteIsolationPolicy::IsTopDocumentIsolationEnabled());
render_process_host = GetDefaultSubframeProcessHost(
browser_context, site_instance, is_for_guests_only);
+ case SiteInstanceImpl::ProcessReusePolicy::REUSE_PENDING_OR_COMMITTED_SITE:
+ render_process_host =
+ FindReusableProcessHostForSite(browser_context, site_url);
break;
default:
break;
@@ -3257,6 +3397,55 @@ RenderProcessHost* RenderProcessHostImpl::GetDefaultSubframeProcessHost(
return holder->GetProcessHost(site_instance, is_for_guests_only);
}
+// static
+RenderProcessHost* RenderProcessHostImpl::FindReusableProcessHostForSite(
+ BrowserContext* browser_context,
+ const GURL& site_url) {
+ if (site_url.is_empty())
+ return nullptr;
+
+ std::set<RenderProcessHost*> eligible_foreground_hosts;
+ std::set<RenderProcessHost*> eligible_background_hosts;
+
+ // Add the RenderProcessHosts hosting a frame for |site_url| to the list of
+ // eligible RenderProcessHosts.
+ SiteCountPerProcessTracker* committed_tracker =
+ static_cast<SiteCountPerProcessTracker*>(browser_context->GetUserData(
+ kCommittedSiteCountPerProcessTrackerKey));
+ if (committed_tracker) {
+ committed_tracker->FindRenderProcessesForSite(
+ site_url, &eligible_foreground_hosts, &eligible_background_hosts);
+ }
+
+ // Add the RenderProcessHosts expecting a navigation to |site_url| to the list
+ // of eligible RenderProcessHosts.
+ SiteCountPerProcessTracker* pending_tracker =
+ static_cast<SiteCountPerProcessTracker*>(
+ browser_context->GetUserData(kPendingSiteCountPerProcessTrackerKey));
+ if (pending_tracker) {
+ pending_tracker->FindRenderProcessesForSite(
+ site_url, &eligible_foreground_hosts, &eligible_background_hosts);
+ }
+
+ if (!eligible_foreground_hosts.empty()) {
+ int index = base::RandInt(0, eligible_foreground_hosts.size() - 1);
+ auto iterator = eligible_foreground_hosts.begin();
+ for (int i = 0; i < index; ++i)
+ ++iterator;
+ return (*iterator);
+ }
+
+ if (!eligible_background_hosts.empty()) {
+ int index = base::RandInt(0, eligible_background_hosts.size() - 1);
+ auto iterator = eligible_background_hosts.begin();
+ for (int i = 0; i < index; ++i)
+ ++iterator;
+ return (*iterator);
+ }
+
+ return nullptr;
+}
+
#if BUILDFLAG(ENABLE_WEBRTC)
void RenderProcessHostImpl::OnRegisterAecDumpConsumer(int id) {
BrowserThread::PostTask(

Powered by Google App Engine
This is Rietveld 408576698