Chromium Code Reviews| Index: content/renderer/render_thread_impl.cc |
| diff --git a/content/renderer/render_thread_impl.cc b/content/renderer/render_thread_impl.cc |
| index a47ea0cabcb928515ae5a1c599a926e35c2ab0b3..aeeb518a407eb5c71c1f899a35d41b7c8ea76f69 100644 |
| --- a/content/renderer/render_thread_impl.cc |
| +++ b/content/renderer/render_thread_impl.cc |
| @@ -101,6 +101,9 @@ using content::RenderProcessObserver; |
| namespace { |
| static const int64 kInitialIdleHandlerDelayMs = 1000; |
| +static const int64 kShortIdleHandlerDelayMs = 1000; |
| +static const int64 kLongIdleHandlerDelayMs = 30*1000; |
| +static const int kIdleCPUUsageThresholdInPercents = 3; |
| #if defined(TOUCH_UI) |
| static const int kPopupListBoxMinimumRowHeight = 60; |
| @@ -193,6 +196,15 @@ void RenderThreadImpl::Init() { |
| widget_count_ = 0; |
| hidden_widget_count_ = 0; |
| idle_notification_delay_in_ms_ = kInitialIdleHandlerDelayMs; |
| + idle_notifications_to_skip_ = 0; |
| + base::ProcessHandle handle = base::GetCurrentProcessHandle(); |
| +#if defined(OS_MACOSX) |
| + process_metrics_.reset(base::ProcessMetrics::CreateProcessMetrics(handle, |
| + NULL)); |
| +#else |
| + process_metrics_.reset(base::ProcessMetrics::CreateProcessMetrics(handle)); |
| +#endif |
| + process_metrics_->GetCPUUsage(); // Initialize CPU usage counters. |
| task_factory_.reset(new ScopedRunnableMethodFactory<RenderThreadImpl>(this)); |
| appcache_dispatcher_.reset(new AppCacheDispatcher(Get())); |
| @@ -415,7 +427,7 @@ void RenderThreadImpl::WidgetRestored() { |
| return; |
| } |
| - idle_timer_.Stop(); |
| + ScheduleIdleHandler(kLongIdleHandlerDelayMs); |
| } |
| void RenderThreadImpl::EnsureWebKitInitialized() { |
| @@ -524,6 +536,11 @@ void RenderThreadImpl::EnsureWebKitInitialized() { |
| WebRuntimeFeatures::enableQuota(true); |
| FOR_EACH_OBSERVER(RenderProcessObserver, observers_, WebKitInitialized()); |
| + |
| + if (content::GetContentClient()->renderer()-> |
| + RunIdleHandlerWhenWidgetsHidden()) { |
| + ScheduleIdleHandler(kLongIdleHandlerDelayMs); |
| + } |
| } |
| void RenderThreadImpl::RecordUserMetrics(const std::string& action) { |
| @@ -557,7 +574,14 @@ void RenderThreadImpl::ScheduleIdleHandler(int64 initial_delay_ms) { |
| } |
| void RenderThreadImpl::IdleHandler() { |
| - #if !defined(OS_MACOSX) && defined(USE_TCMALLOC) |
| + bool is_extension = !content::GetContentClient()->renderer()-> |
|
Matt Perry
2011/11/16 19:23:52
extensions are a chrome concept, and this code liv
ulan
2011/11/16 20:13:22
Done.
|
| + RunIdleHandlerWhenWidgetsHidden(); |
| + bool foreground_tab = (widget_count_ > hidden_widget_count_) && !is_extension; |
| + if (foreground_tab) { |
| + IdleHandlerInForegroundTab(); |
| + return; |
| + } |
| +#if !defined(OS_MACOSX) && defined(USE_TCMALLOC) |
| MallocExtension::instance()->ReleaseFreeMemory(); |
| #endif |
| @@ -589,6 +613,10 @@ void RenderThreadImpl::SetIdleNotificationDelayInMs( |
| idle_notification_delay_in_ms_ = idle_notification_delay_in_ms; |
| } |
| +void RenderThreadImpl::PostponeIdleNotification() { |
| + idle_notifications_to_skip_ = 2; |
| +} |
| + |
| #if defined(OS_WIN) |
| void RenderThreadImpl::PreCacheFont(const LOGFONT& log_font) { |
| Send(new ChildProcessHostMsg_PreCacheFont(log_font)); |
| @@ -783,6 +811,28 @@ void RenderThreadImpl::OnTempCrashWithData(const GURL& data) { |
| CHECK(false); |
| } |
| +void RenderThreadImpl::IdleHandlerInForegroundTab() { |
|
Matt Perry
2011/11/16 19:23:52
could you move this next to the other IdleHandler,
ulan
2011/11/16 20:13:22
Done.
|
| + // Increase the delay in the same way as in IdleHandler, |
| + // but make it periodic by reseting it once it is too big. |
| + int64 new_delay_ms = idle_notification_delay_in_ms_ + |
| + 1000000 / (idle_notification_delay_in_ms_ + 2000); |
| + if (new_delay_ms >= kLongIdleHandlerDelayMs) |
| + new_delay_ms = kShortIdleHandlerDelayMs; |
| + |
| + double cpu_usage = process_metrics_->GetCPUUsage(); |
|
ulan
2011/11/16 14:14:46
I didn't place GetCPUUsage inside the "if" stateme
Matt Perry
2011/11/16 19:23:52
Add this as a comment in the code, so someone read
ulan
2011/11/16 20:13:22
Done.
|
| + |
| + if (idle_notifications_to_skip_ > 0) { |
| + idle_notifications_to_skip_--; |
| + } else if (cpu_usage < kIdleCPUUsageThresholdInPercents) { |
| + if (v8::V8::IdleNotification()) { |
| + // V8 finished collecting garbage. |
| + new_delay_ms = kLongIdleHandlerDelayMs; |
| + } |
| + } |
| + |
| + ScheduleIdleHandler(new_delay_ms); |
| +} |
| + |
| scoped_refptr<base::MessageLoopProxy> |
| RenderThreadImpl::GetFileThreadMessageLoopProxy() { |
| DCHECK(message_loop() == MessageLoop::current()); |