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 #include "chrome/browser/prerender/prerender_manager.h" | 5 #include "chrome/browser/prerender/prerender_manager.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 | 8 |
| 9 #include <algorithm> | 9 #include <algorithm> |
| 10 #include <functional> | 10 #include <functional> |
| (...skipping 307 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 318 | 318 |
| 319 PrerenderHandle* PrerenderManager::AddPrerenderForInstant( | 319 PrerenderHandle* PrerenderManager::AddPrerenderForInstant( |
| 320 const GURL& url, | 320 const GURL& url, |
| 321 content::SessionStorageNamespace* session_storage_namespace, | 321 content::SessionStorageNamespace* session_storage_namespace, |
| 322 const gfx::Size& size) { | 322 const gfx::Size& size) { |
| 323 DCHECK(search::ShouldPrefetchSearchResults()); | 323 DCHECK(search::ShouldPrefetchSearchResults()); |
| 324 return AddPrerender(ORIGIN_INSTANT, url, content::Referrer(), size, | 324 return AddPrerender(ORIGIN_INSTANT, url, content::Referrer(), size, |
| 325 session_storage_namespace); | 325 session_storage_namespace); |
| 326 } | 326 } |
| 327 | 327 |
| 328 PrerenderHandle* PrerenderManager::AddPrerenderForOffline( | |
| 329 const GURL& url, | |
| 330 content::SessionStorageNamespace* session_storage_namespace, | |
| 331 const gfx::Size& size) { | |
| 332 return AddPrerender(ORIGIN_OFFLINE, url, content::Referrer(), size, | |
| 333 session_storage_namespace); | |
| 334 } | |
| 335 | |
| 328 void PrerenderManager::CancelAllPrerenders() { | 336 void PrerenderManager::CancelAllPrerenders() { |
| 329 DCHECK(CalledOnValidThread()); | 337 DCHECK(CalledOnValidThread()); |
| 330 while (!active_prerenders_.empty()) { | 338 while (!active_prerenders_.empty()) { |
| 331 PrerenderContents* prerender_contents = | 339 PrerenderContents* prerender_contents = |
| 332 active_prerenders_.front()->contents(); | 340 active_prerenders_.front()->contents(); |
| 333 prerender_contents->Destroy(FINAL_STATUS_CANCELLED); | 341 prerender_contents->Destroy(FINAL_STATUS_CANCELLED); |
| 334 } | 342 } |
| 335 } | 343 } |
| 336 | 344 |
| 337 bool PrerenderManager::MaybeUsePrerenderedPage(const GURL& url, | 345 bool PrerenderManager::MaybeUsePrerenderedPage(const GURL& url, |
| (...skipping 611 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 949 | 957 |
| 950 GURL url = url_arg; | 958 GURL url = url_arg; |
| 951 GURL alias_url; | 959 GURL alias_url; |
| 952 if (IsControlGroup() && MaybeGetQueryStringBasedAliasURL(url, &alias_url)) | 960 if (IsControlGroup() && MaybeGetQueryStringBasedAliasURL(url, &alias_url)) |
| 953 url = alias_url; | 961 url = alias_url; |
| 954 | 962 |
| 955 // From here on, we will record a FinalStatus so we need to register with the | 963 // From here on, we will record a FinalStatus so we need to register with the |
| 956 // histogram tracking. | 964 // histogram tracking. |
| 957 histograms_->RecordPrerender(origin, url_arg); | 965 histograms_->RecordPrerender(origin, url_arg); |
| 958 | 966 |
| 959 if (profile_->GetPrefs()->GetBoolean(prefs::kBlockThirdPartyCookies)) { | 967 if (profile_->GetPrefs()->GetBoolean(prefs::kBlockThirdPartyCookies) && |
| 968 origin != ORIGIN_OFFLINE) { | |
| 960 RecordFinalStatusWithoutCreatingPrerenderContents( | 969 RecordFinalStatusWithoutCreatingPrerenderContents( |
| 961 url, origin, FINAL_STATUS_BLOCK_THIRD_PARTY_COOKIES); | 970 url, origin, FINAL_STATUS_BLOCK_THIRD_PARTY_COOKIES); |
| 962 return nullptr; | 971 return nullptr; |
| 963 } | 972 } |
| 964 | 973 |
| 965 NetworkPredictionStatus prerendering_status = | 974 NetworkPredictionStatus prerendering_status = |
| 966 GetPredictionStatusForOrigin(origin); | 975 GetPredictionStatusForOrigin(origin); |
| 967 if (prerendering_status != NetworkPredictionStatus::ENABLED) { | 976 if (prerendering_status != NetworkPredictionStatus::ENABLED) { |
| 968 FinalStatus final_status = | 977 FinalStatus final_status = |
| 969 prerendering_status == NetworkPredictionStatus::DISABLED_DUE_TO_NETWORK | 978 prerendering_status == NetworkPredictionStatus::DISABLED_DUE_TO_NETWORK |
| 970 ? FINAL_STATUS_CELLULAR_NETWORK | 979 ? FINAL_STATUS_CELLULAR_NETWORK |
| 971 : FINAL_STATUS_PRERENDERING_DISABLED; | 980 : FINAL_STATUS_PRERENDERING_DISABLED; |
| 972 RecordFinalStatusWithoutCreatingPrerenderContents(url, origin, | 981 RecordFinalStatusWithoutCreatingPrerenderContents(url, origin, |
| 973 final_status); | 982 final_status); |
| 974 return nullptr; | 983 return nullptr; |
| 975 } | 984 } |
| 976 | 985 |
| 977 if (PrerenderData* preexisting_prerender_data = | 986 if (PrerenderData* preexisting_prerender_data = |
| 978 FindPrerenderData(url, session_storage_namespace)) { | 987 FindPrerenderData(url, session_storage_namespace)) { |
| 979 RecordFinalStatusWithoutCreatingPrerenderContents( | 988 RecordFinalStatusWithoutCreatingPrerenderContents( |
| 980 url, origin, FINAL_STATUS_DUPLICATE); | 989 url, origin, FINAL_STATUS_DUPLICATE); |
|
gabadie
2016/04/25 12:35:12
Duplicated offline prerender would no longer be de
pasko
2016/04/25 13:03:56
I think it is good enough. In worst case we run th
| |
| 981 return new PrerenderHandle(preexisting_prerender_data); | 990 return new PrerenderHandle(preexisting_prerender_data); |
| 982 } | 991 } |
| 983 | 992 |
| 984 // Do not prerender if there are too many render processes, and we would | 993 // Do not prerender if there are too many render processes, and we would |
| 985 // have to use an existing one. We do not want prerendering to happen in | 994 // have to use an existing one. We do not want prerendering to happen in |
| 986 // a shared process, so that we can always reliably lower the CPU | 995 // a shared process, so that we can always reliably lower the CPU |
| 987 // priority for prerendering. | 996 // priority for prerendering. |
| 988 // In single-process mode, ShouldTryToUseExistingProcessHost() always returns | 997 // In single-process mode, ShouldTryToUseExistingProcessHost() always returns |
| 989 // true, so that case needs to be explicitly checked for. | 998 // true, so that case needs to be explicitly checked for. |
| 990 // TODO(tburkard): Figure out how to cancel prerendering in the opposite | 999 // TODO(tburkard): Figure out how to cancel prerendering in the opposite |
| (...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1145 void PrerenderManager::SortActivePrerenders() { | 1154 void PrerenderManager::SortActivePrerenders() { |
| 1146 std::sort(active_prerenders_.begin(), active_prerenders_.end(), | 1155 std::sort(active_prerenders_.begin(), active_prerenders_.end(), |
| 1147 PrerenderData::OrderByExpiryTime()); | 1156 PrerenderData::OrderByExpiryTime()); |
| 1148 } | 1157 } |
| 1149 | 1158 |
| 1150 PrerenderManager::PrerenderData* PrerenderManager::FindPrerenderData( | 1159 PrerenderManager::PrerenderData* PrerenderManager::FindPrerenderData( |
| 1151 const GURL& url, | 1160 const GURL& url, |
| 1152 const SessionStorageNamespace* session_storage_namespace) { | 1161 const SessionStorageNamespace* session_storage_namespace) { |
| 1153 for (ScopedVector<PrerenderData>::iterator it = active_prerenders_.begin(); | 1162 for (ScopedVector<PrerenderData>::iterator it = active_prerenders_.begin(); |
| 1154 it != active_prerenders_.end(); ++it) { | 1163 it != active_prerenders_.end(); ++it) { |
| 1155 if ((*it)->contents()->Matches(url, session_storage_namespace)) | 1164 PrerenderContents* contents = (*it)->contents(); |
| 1165 if (contents->Matches(url, session_storage_namespace)) { | |
| 1166 if (contents->origin() == ORIGIN_OFFLINE) | |
| 1167 return NULL; | |
| 1156 return *it; | 1168 return *it; |
| 1169 } | |
| 1157 } | 1170 } |
| 1158 return NULL; | 1171 return NULL; |
| 1159 } | 1172 } |
| 1160 | 1173 |
| 1161 ScopedVector<PrerenderManager::PrerenderData>::iterator | 1174 ScopedVector<PrerenderManager::PrerenderData>::iterator |
| 1162 PrerenderManager::FindIteratorForPrerenderContents( | 1175 PrerenderManager::FindIteratorForPrerenderContents( |
| 1163 PrerenderContents* prerender_contents) { | 1176 PrerenderContents* prerender_contents) { |
| 1164 for (ScopedVector<PrerenderData>::iterator it = active_prerenders_.begin(); | 1177 for (ScopedVector<PrerenderData>::iterator it = active_prerenders_.begin(); |
| 1165 it != active_prerenders_.end(); ++it) { | 1178 it != active_prerenders_.end(); ++it) { |
| 1166 if (prerender_contents == (*it)->contents()) | 1179 if (prerender_contents == (*it)->contents()) |
| 1167 return it; | 1180 return it; |
| 1168 } | 1181 } |
| 1169 return active_prerenders_.end(); | 1182 return active_prerenders_.end(); |
| 1170 } | 1183 } |
| 1171 | 1184 |
| 1172 bool PrerenderManager::DoesRateLimitAllowPrerender(Origin origin) const { | 1185 bool PrerenderManager::DoesRateLimitAllowPrerender(Origin origin) const { |
| 1173 DCHECK(CalledOnValidThread()); | 1186 DCHECK(CalledOnValidThread()); |
| 1174 base::TimeDelta elapsed_time = | 1187 base::TimeDelta elapsed_time = |
| 1175 GetCurrentTimeTicks() - last_prerender_start_time_; | 1188 GetCurrentTimeTicks() - last_prerender_start_time_; |
| 1176 histograms_->RecordTimeBetweenPrerenderRequests(origin, elapsed_time); | 1189 histograms_->RecordTimeBetweenPrerenderRequests(origin, elapsed_time); |
| 1190 // TODO(gabadie,pasko): Re-implement missing tests for | |
| 1191 // FINAL_STATUS_RATE_LIMIT_EXCEEDED that where removed by: | |
| 1192 // http://crrev.com/a2439eeab37f7cb7a118493fb55ec0cb07f93b49. | |
| 1193 if (origin == ORIGIN_OFFLINE) | |
| 1194 return true; | |
| 1177 if (!config_.rate_limit_enabled) | 1195 if (!config_.rate_limit_enabled) |
| 1178 return true; | 1196 return true; |
| 1179 return elapsed_time >= | 1197 return elapsed_time >= |
| 1180 base::TimeDelta::FromMilliseconds(kMinTimeBetweenPrerendersMs); | 1198 base::TimeDelta::FromMilliseconds(kMinTimeBetweenPrerendersMs); |
| 1181 } | 1199 } |
| 1182 | 1200 |
| 1183 void PrerenderManager::DeleteOldWebContents() { | 1201 void PrerenderManager::DeleteOldWebContents() { |
| 1184 while (!old_web_contents_list_.empty()) { | 1202 while (!old_web_contents_list_.empty()) { |
| 1185 WebContents* web_contents = old_web_contents_list_.front(); | 1203 WebContents* web_contents = old_web_contents_list_.front(); |
| 1186 old_web_contents_list_.pop_front(); | 1204 old_web_contents_list_.pop_front(); |
| (...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1309 | 1327 |
| 1310 NetworkPredictionStatus PrerenderManager::GetPredictionStatus() const { | 1328 NetworkPredictionStatus PrerenderManager::GetPredictionStatus() const { |
| 1311 DCHECK(CalledOnValidThread()); | 1329 DCHECK(CalledOnValidThread()); |
| 1312 return CanPrefetchAndPrerenderUI(profile_->GetPrefs()); | 1330 return CanPrefetchAndPrerenderUI(profile_->GetPrefs()); |
| 1313 } | 1331 } |
| 1314 | 1332 |
| 1315 NetworkPredictionStatus PrerenderManager::GetPredictionStatusForOrigin( | 1333 NetworkPredictionStatus PrerenderManager::GetPredictionStatusForOrigin( |
| 1316 Origin origin) const { | 1334 Origin origin) const { |
| 1317 DCHECK(CalledOnValidThread()); | 1335 DCHECK(CalledOnValidThread()); |
| 1318 | 1336 |
| 1319 // LINK rel=prerender origins ignore the network state and the privacy | 1337 // <link rel=prerender> origins ignore the network state and the privacy |
| 1320 // settings. | 1338 // settings. Web developers should be able prefetch with all possible privacy |
| 1339 // settings and with all possible network types. This would avoid web devs | |
| 1340 // coming up with creative ways to prefetch in cases they are not allowed to | |
| 1341 // do so. | |
| 1342 // | |
| 1343 // Offline originated prerenders also ignore the network state and privacy | |
| 1344 // settings because they are controlled by the offliner logic via | |
| 1345 // PrerenderHandle. | |
| 1321 if (origin == ORIGIN_LINK_REL_PRERENDER_SAMEDOMAIN || | 1346 if (origin == ORIGIN_LINK_REL_PRERENDER_SAMEDOMAIN || |
| 1322 origin == ORIGIN_LINK_REL_PRERENDER_CROSSDOMAIN) { | 1347 origin == ORIGIN_LINK_REL_PRERENDER_CROSSDOMAIN || |
| 1348 origin == ORIGIN_OFFLINE) { | |
| 1323 return NetworkPredictionStatus::ENABLED; | 1349 return NetworkPredictionStatus::ENABLED; |
| 1324 } | 1350 } |
| 1325 | 1351 |
| 1326 // Prerendering forced for cellular networks still prevents navigation with | 1352 // Prerendering forced for cellular networks still prevents navigation with |
| 1327 // the DISABLED_ALWAYS selected via privacy settings. | 1353 // the DISABLED_ALWAYS selected via privacy settings. |
| 1328 NetworkPredictionStatus prediction_status = | 1354 NetworkPredictionStatus prediction_status = |
| 1329 CanPrefetchAndPrerenderUI(profile_->GetPrefs()); | 1355 CanPrefetchAndPrerenderUI(profile_->GetPrefs()); |
| 1330 if (origin == ORIGIN_EXTERNAL_REQUEST_FORCED_CELLULAR && | 1356 if (origin == ORIGIN_EXTERNAL_REQUEST_FORCED_CELLULAR && |
| 1331 prediction_status == NetworkPredictionStatus::DISABLED_DUE_TO_NETWORK) { | 1357 prediction_status == NetworkPredictionStatus::DISABLED_DUE_TO_NETWORK) { |
| 1332 return NetworkPredictionStatus::ENABLED; | 1358 return NetworkPredictionStatus::ENABLED; |
| (...skipping 27 matching lines...) Expand all Loading... | |
| 1360 } | 1386 } |
| 1361 | 1387 |
| 1362 void PrerenderManager::RenderProcessHostDestroyed( | 1388 void PrerenderManager::RenderProcessHostDestroyed( |
| 1363 content::RenderProcessHost* host) { | 1389 content::RenderProcessHost* host) { |
| 1364 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 1390 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
| 1365 size_t erased = prerender_process_hosts_.erase(host); | 1391 size_t erased = prerender_process_hosts_.erase(host); |
| 1366 DCHECK_EQ(1u, erased); | 1392 DCHECK_EQ(1u, erased); |
| 1367 } | 1393 } |
| 1368 | 1394 |
| 1369 } // namespace prerender | 1395 } // namespace prerender |
| OLD | NEW |