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

Side by Side Diff: sky/engine/core/fetch/ResourceFetcher.cpp

Issue 710383002: Remove preload support from the MemoryCache (Closed) Base URL: git@github.com:domokit/mojo.git@master
Patch Set: Created 6 years, 1 month 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 /* 1 /*
2 Copyright (C) 1998 Lars Knoll (knoll@mpi-hd.mpg.de) 2 Copyright (C) 1998 Lars Knoll (knoll@mpi-hd.mpg.de)
3 Copyright (C) 2001 Dirk Mueller (mueller@kde.org) 3 Copyright (C) 2001 Dirk Mueller (mueller@kde.org)
4 Copyright (C) 2002 Waldo Bastian (bastian@kde.org) 4 Copyright (C) 2002 Waldo Bastian (bastian@kde.org)
5 Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved. 5 Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
6 Copyright (C) 2009 Torch Mobile Inc. http://www.torchmobile.com/ 6 Copyright (C) 2009 Torch Mobile Inc. http://www.torchmobile.com/
7 7
8 This library is free software; you can redistribute it and/or 8 This library is free software; you can redistribute it and/or
9 modify it under the terms of the GNU Library General Public 9 modify it under the terms of the GNU Library General Public
10 License as published by the Free Software Foundation; either 10 License as published by the Free Software Foundation; either
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
51 #include "platform/RuntimeEnabledFeatures.h" 51 #include "platform/RuntimeEnabledFeatures.h"
52 #include "platform/SharedBuffer.h" 52 #include "platform/SharedBuffer.h"
53 #include "platform/TraceEvent.h" 53 #include "platform/TraceEvent.h"
54 #include "platform/weborigin/SecurityPolicy.h" 54 #include "platform/weborigin/SecurityPolicy.h"
55 #include "public/platform/Platform.h" 55 #include "public/platform/Platform.h"
56 #include "public/platform/WebURL.h" 56 #include "public/platform/WebURL.h"
57 #include "public/platform/WebURLRequest.h" 57 #include "public/platform/WebURLRequest.h"
58 #include "wtf/text/CString.h" 58 #include "wtf/text/CString.h"
59 #include "wtf/text/WTFString.h" 59 #include "wtf/text/WTFString.h"
60 60
61 #define PRELOAD_DEBUG 0
62
63 using blink::WebURLRequest; 61 using blink::WebURLRequest;
64 62
65 namespace blink { 63 namespace blink {
66 64
67 static Resource* createResource(Resource::Type type, const ResourceRequest& requ est, const String& charset) 65 static Resource* createResource(Resource::Type type, const ResourceRequest& requ est, const String& charset)
68 { 66 {
69 switch (type) { 67 switch (type) {
70 case Resource::Image: 68 case Resource::Image:
71 return new ImageResource(request); 69 return new ImageResource(request);
72 case Resource::Font: 70 case Resource::Font:
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
146 , m_autoLoadImages(true) 144 , m_autoLoadImages(true)
147 , m_imagesEnabled(true) 145 , m_imagesEnabled(true)
148 , m_allowStaleResources(false) 146 , m_allowStaleResources(false)
149 { 147 {
150 } 148 }
151 149
152 ResourceFetcher::~ResourceFetcher() 150 ResourceFetcher::~ResourceFetcher()
153 { 151 {
154 m_document = nullptr; 152 m_document = nullptr;
155 153
156 clearPreloads();
157
158 // Make sure no requests still point to this ResourceFetcher 154 // Make sure no requests still point to this ResourceFetcher
159 ASSERT(!m_requestCount); 155 ASSERT(!m_requestCount);
160 } 156 }
161 157
162 Resource* ResourceFetcher::cachedResource(const KURL& resourceURL) const 158 Resource* ResourceFetcher::cachedResource(const KURL& resourceURL) const
163 { 159 {
164 KURL url = MemoryCache::removeFragmentIdentifierIfNeeded(resourceURL); 160 KURL url = MemoryCache::removeFragmentIdentifierIfNeeded(resourceURL);
165 return m_documentResources.get(url).get(); 161 return m_documentResources.get(url).get();
166 } 162 }
167 163
(...skipping 23 matching lines...) Expand all
191 return resource && resource->type() == Resource::Image ? toImageResource(res ource) : 0; 187 return resource && resource->type() == Resource::Image ? toImageResource(res ource) : 0;
192 } 188 }
193 189
194 ResourcePtr<FontResource> ResourceFetcher::fetchFont(FetchRequest& request) 190 ResourcePtr<FontResource> ResourceFetcher::fetchFont(FetchRequest& request)
195 { 191 {
196 ASSERT(request.resourceRequest().frameType() == WebURLRequest::FrameTypeNone ); 192 ASSERT(request.resourceRequest().frameType() == WebURLRequest::FrameTypeNone );
197 request.mutableResourceRequest().setRequestContext(WebURLRequest::RequestCon textFont); 193 request.mutableResourceRequest().setRequestContext(WebURLRequest::RequestCon textFont);
198 return toFontResource(requestResource(Resource::Font, request)); 194 return toFontResource(requestResource(Resource::Font, request));
199 } 195 }
200 196
201 bool ResourceFetcher::canRequest(Resource::Type type, const KURL& url, const Res ourceLoaderOptions& options, bool forPreload, FetchRequest::OriginRestriction or iginRestriction) const 197 bool ResourceFetcher::canRequest(Resource::Type type, const KURL& url, const Res ourceLoaderOptions& options, FetchRequest::OriginRestriction originRestriction) const
202 { 198 {
203 // FIXME(sky): Remove 199 // FIXME(sky): Remove
204 return true; 200 return true;
205 } 201 }
206 202
207 bool ResourceFetcher::shouldLoadNewResource(Resource::Type type) const 203 bool ResourceFetcher::shouldLoadNewResource(Resource::Type type) const
208 { 204 {
209 if (!frame()) 205 if (!frame())
210 return false; 206 return false;
211 return true; 207 return true;
(...skipping 20 matching lines...) Expand all
232 } 228 }
233 229
234 ResourcePtr<Resource> ResourceFetcher::requestResource(Resource::Type type, Fetc hRequest& request) 230 ResourcePtr<Resource> ResourceFetcher::requestResource(Resource::Type type, Fetc hRequest& request)
235 { 231 {
236 ASSERT(request.options().synchronousPolicy == RequestAsynchronously || type == Resource::Raw); 232 ASSERT(request.options().synchronousPolicy == RequestAsynchronously || type == Resource::Raw);
237 233
238 TRACE_EVENT0("blink", "ResourceFetcher::requestResource"); 234 TRACE_EVENT0("blink", "ResourceFetcher::requestResource");
239 235
240 KURL url = request.resourceRequest().url(); 236 KURL url = request.resourceRequest().url();
241 237
242 WTF_LOG(ResourceLoading, "ResourceFetcher::requestResource '%s', charset '%s ', priority=%d, forPreload=%u, type=%s", url.elidedString().latin1().data(), req uest.charset().latin1().data(), request.priority(), request.forPreload(), Resour ceTypeName(type)); 238 WTF_LOG(ResourceLoading, "ResourceFetcher::requestResource '%s', charset '%s ', priority=%d, type=%s", url.elidedString().latin1().data(), request.charset(). latin1().data(), request.priority(), ResourceTypeName(type));
243 239
244 // If only the fragment identifiers differ, it is the same resource. 240 // If only the fragment identifiers differ, it is the same resource.
245 url = MemoryCache::removeFragmentIdentifierIfNeeded(url); 241 url = MemoryCache::removeFragmentIdentifierIfNeeded(url);
246 242
247 if (!url.isValid()) 243 if (!url.isValid())
248 return 0; 244 return 0;
249 245
250 if (!canRequest(type, url, request.options(), request.forPreload(), request. originRestriction())) 246 if (!canRequest(type, url, request.options(), request.originRestriction()))
251 return 0; 247 return 0;
252 248
253 if (LocalFrame* f = frame()) 249 if (LocalFrame* f = frame())
254 f->loaderClient()->dispatchWillRequestResource(&request); 250 f->loaderClient()->dispatchWillRequestResource(&request);
255 251
256 // See if we can use an existing resource from the cache. 252 // See if we can use an existing resource from the cache.
257 ResourcePtr<Resource> resource = memoryCache()->resourceForURL(url); 253 ResourcePtr<Resource> resource = memoryCache()->resourceForURL(url);
258 254
259 const RevalidationPolicy policy = determineRevalidationPolicy(type, request, resource.get()); 255 const RevalidationPolicy policy = determineRevalidationPolicy(type, request, resource.get());
260 switch (policy) { 256 switch (policy) {
(...skipping 13 matching lines...) Expand all
274 270
275 if (!resource) 271 if (!resource)
276 return 0; 272 return 0;
277 273
278 if (!resource->hasClients()) 274 if (!resource->hasClients())
279 m_deadStatsRecorder.update(policy); 275 m_deadStatsRecorder.update(policy);
280 276
281 if (policy != Use) 277 if (policy != Use)
282 resource->setIdentifier(createUniqueIdentifier()); 278 resource->setIdentifier(createUniqueIdentifier());
283 279
284 if (!request.forPreload() || policy != Use) { 280 ResourceLoadPriority priority = loadPriority(type, request);
285 ResourceLoadPriority priority = loadPriority(type, request); 281 if (priority != resource->resourceRequest().priority()) {
286 if (priority != resource->resourceRequest().priority()) { 282 resource->mutableResourceRequest().setPriority(priority);
287 resource->mutableResourceRequest().setPriority(priority); 283 resource->didChangePriority(priority, 0);
288 resource->didChangePriority(priority, 0);
289 }
290 } 284 }
291 285
292 if (resourceNeedsLoad(resource.get(), request, policy)) { 286 if (resourceNeedsLoad(resource.get(), request, policy)) {
293 if (!shouldLoadNewResource(type)) { 287 if (!shouldLoadNewResource(type)) {
294 if (memoryCache()->contains(resource.get())) 288 if (memoryCache()->contains(resource.get()))
295 memoryCache()->remove(resource.get()); 289 memoryCache()->remove(resource.get());
296 return 0; 290 return 0;
297 } 291 }
298 292
299 resource->load(this, request.options()); 293 resource->load(this, request.options());
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
394 return resource; 388 return resource;
395 } 389 }
396 390
397 ResourceFetcher::RevalidationPolicy ResourceFetcher::determineRevalidationPolicy (Resource::Type type, const FetchRequest& fetchRequest, Resource* existingResour ce) const 391 ResourceFetcher::RevalidationPolicy ResourceFetcher::determineRevalidationPolicy (Resource::Type type, const FetchRequest& fetchRequest, Resource* existingResour ce) const
398 { 392 {
399 const ResourceRequest& request = fetchRequest.resourceRequest(); 393 const ResourceRequest& request = fetchRequest.resourceRequest();
400 394
401 if (!existingResource) 395 if (!existingResource)
402 return Load; 396 return Load;
403 397
404 // We already have a preload going for this URL.
405 if (fetchRequest.forPreload() && existingResource->isPreloaded())
406 return Use;
407
408 // If the same URL has been loaded as a different type, we need to reload. 398 // If the same URL has been loaded as a different type, we need to reload.
409 if (existingResource->type() != type) { 399 if (existingResource->type() != type) {
410 // FIXME: If existingResource is a Preload and the new type is LinkPrefe tch
411 // We really should discard the new prefetch since the preload has more
412 // specific type information! crbug.com/379893
413 // fast/dom/HTMLLinkElement/link-and-subresource-test hits this case.
414 WTF_LOG(ResourceLoading, "ResourceFetcher::determineRevalidationPolicy r eloading due to type mismatch."); 400 WTF_LOG(ResourceLoading, "ResourceFetcher::determineRevalidationPolicy r eloading due to type mismatch.");
415 return Reload; 401 return Reload;
416 } 402 }
417 403
418 // Do not load from cache if images are not enabled. The load for this image will be blocked 404 // Do not load from cache if images are not enabled. The load for this image will be blocked
419 // in ImageResource::load. 405 // in ImageResource::load.
420 if (FetchRequest::DeferredByClient == fetchRequest.defer()) 406 if (FetchRequest::DeferredByClient == fetchRequest.defer())
421 return Reload; 407 return Reload;
422 408
423 // Always use data uris. 409 // Always use data uris.
(...skipping 14 matching lines...) Expand all
438 if (request.isConditional()) 424 if (request.isConditional())
439 return Reload; 425 return Reload;
440 426
441 // Don't reload resources while pasting. 427 // Don't reload resources while pasting.
442 if (m_allowStaleResources) 428 if (m_allowStaleResources)
443 return Use; 429 return Use;
444 430
445 if (!fetchRequest.options().canReuseRequest(existingResource->options())) 431 if (!fetchRequest.options().canReuseRequest(existingResource->options()))
446 return Reload; 432 return Reload;
447 433
448 // Always use preloads.
449 if (existingResource->isPreloaded())
450 return Use;
451
452 // CachePolicyHistoryBuffer uses the cache no matter what. 434 // CachePolicyHistoryBuffer uses the cache no matter what.
453 CachePolicy cachePolicy = context().cachePolicy(document()); 435 CachePolicy cachePolicy = context().cachePolicy(document());
454 if (cachePolicy == CachePolicyHistoryBuffer) 436 if (cachePolicy == CachePolicyHistoryBuffer)
455 return Use; 437 return Use;
456 438
457 // Don't reuse resources with Cache-control: no-store. 439 // Don't reuse resources with Cache-control: no-store.
458 if (existingResource->hasCacheControlNoStoreHeader()) { 440 if (existingResource->hasCacheControlNoStoreHeader()) {
459 WTF_LOG(ResourceLoading, "ResourceFetcher::determineRevalidationPolicy r eloading due to Cache-control: no-store."); 441 WTF_LOG(ResourceLoading, "ResourceFetcher::determineRevalidationPolicy r eloading due to Cache-control: no-store.");
460 return Reload; 442 return Reload;
461 } 443 }
(...skipping 179 matching lines...) Expand 10 before | Expand all | Expand 10 after
641 623
642 void ResourceFetcher::decrementRequestCount(const Resource* res) 624 void ResourceFetcher::decrementRequestCount(const Resource* res)
643 { 625 {
644 if (res->ignoreForRequestCount()) 626 if (res->ignoreForRequestCount())
645 return; 627 return;
646 628
647 --m_requestCount; 629 --m_requestCount;
648 ASSERT(m_requestCount > -1); 630 ASSERT(m_requestCount > -1);
649 } 631 }
650 632
651 void ResourceFetcher::preload(Resource::Type type, FetchRequest& request, const String& charset)
652 {
653 requestPreload(type, request, charset);
654 }
655
656 void ResourceFetcher::requestPreload(Resource::Type type, FetchRequest& request, const String& charset)
657 {
658 // Ensure main resources aren't preloaded, since the cache can't actually re use the preload.
659 if (type == Resource::MainResource)
660 return;
661
662 String encoding;
663 request.setCharset(encoding);
664 request.setForPreload(true);
665
666 ResourcePtr<Resource> resource;
667 // Loading images involves several special cases, so use dedicated fetch met hod instead.
668 if (type == Resource::Image)
669 resource = fetchImage(request);
670 if (!resource)
671 resource = requestResource(type, request);
672 if (!resource || (m_preloads && m_preloads->contains(resource.get())))
673 return;
674 TRACE_EVENT_ASYNC_STEP_INTO0("net", "Resource", resource.get(), "Preload");
675 resource->increasePreloadCount();
676
677 if (!m_preloads)
678 m_preloads = adoptPtr(new ListHashSet<Resource*>);
679 m_preloads->add(resource.get());
680
681 #if PRELOAD_DEBUG
682 printf("PRELOADING %s\n", resource->url().string().latin1().data());
683 #endif
684 }
685
686 bool ResourceFetcher::isPreloaded(const String& urlString) const
687 {
688 const KURL& url = m_document->completeURL(urlString);
689
690 if (m_preloads) {
691 ListHashSet<Resource*>::iterator end = m_preloads->end();
692 for (ListHashSet<Resource*>::iterator it = m_preloads->begin(); it != en d; ++it) {
693 Resource* resource = *it;
694 if (resource->url() == url)
695 return true;
696 }
697 }
698
699 return false;
700 }
701
702 void ResourceFetcher::clearPreloads()
703 {
704 #if PRELOAD_DEBUG
705 printPreloadStats();
706 #endif
707 if (!m_preloads)
708 return;
709
710 ListHashSet<Resource*>::iterator end = m_preloads->end();
711 for (ListHashSet<Resource*>::iterator it = m_preloads->begin(); it != end; + +it) {
712 Resource* res = *it;
713 res->decreasePreloadCount();
714 bool deleted = res->deleteIfPossible();
715 if (!deleted && res->preloadResult() == Resource::PreloadNotReferenced)
716 memoryCache()->remove(res);
717 }
718 m_preloads.clear();
719 }
720
721 void ResourceFetcher::didFinishLoading(const Resource* resource, double finishTi me, int64_t encodedDataLength) 633 void ResourceFetcher::didFinishLoading(const Resource* resource, double finishTi me, int64_t encodedDataLength)
722 { 634 {
723 TRACE_EVENT_ASYNC_END0("net", "Resource", resource); 635 TRACE_EVENT_ASYNC_END0("net", "Resource", resource);
724 context().dispatchDidFinishLoading(m_document, resource->identifier(), finis hTime, encodedDataLength); 636 context().dispatchDidFinishLoading(m_document, resource->identifier(), finis hTime, encodedDataLength);
725 } 637 }
726 638
727 void ResourceFetcher::didChangeLoadingPriority(const Resource* resource, Resourc eLoadPriority loadPriority, int intraPriorityValue) 639 void ResourceFetcher::didChangeLoadingPriority(const Resource* resource, Resourc eLoadPriority loadPriority, int intraPriorityValue)
728 { 640 {
729 TRACE_EVENT_ASYNC_STEP_INTO1("net", "Resource", resource, "ChangePriority", "priority", loadPriority); 641 TRACE_EVENT_ASYNC_STEP_INTO1("net", "Resource", resource, "ChangePriority", "priority", loadPriority);
730 context().dispatchDidChangeResourcePriority(resource->identifier(), loadPrio rity, intraPriorityValue); 642 context().dispatchDidChangeResourcePriority(resource->identifier(), loadPrio rity, intraPriorityValue);
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
810 { 722 {
811 ref(); 723 ref();
812 } 724 }
813 725
814 void ResourceFetcher::derefResourceLoaderHost() 726 void ResourceFetcher::derefResourceLoaderHost()
815 { 727 {
816 deref(); 728 deref();
817 } 729 }
818 #endif 730 #endif
819 731
820 #if PRELOAD_DEBUG
821 void ResourceFetcher::printPreloadStats()
822 {
823 if (!m_preloads)
824 return;
825
826 unsigned scripts = 0;
827 unsigned scriptMisses = 0;
828 unsigned stylesheets = 0;
829 unsigned stylesheetMisses = 0;
830 unsigned images = 0;
831 unsigned imageMisses = 0;
832 ListHashSet<Resource*>::iterator end = m_preloads->end();
833 for (ListHashSet<Resource*>::iterator it = m_preloads->begin(); it != end; + +it) {
834 Resource* res = *it;
835 if (res->preloadResult() == Resource::PreloadNotReferenced)
836 printf("!! UNREFERENCED PRELOAD %s\n", res->url().string().latin1(). data());
837 else if (res->preloadResult() == Resource::PreloadReferencedWhileComplet e)
838 printf("HIT COMPLETE PRELOAD %s\n", res->url().string().latin1().dat a());
839 else if (res->preloadResult() == Resource::PreloadReferencedWhileLoading )
840 printf("HIT LOADING PRELOAD %s\n", res->url().string().latin1().data ());
841
842 images++;
843 if (res->preloadResult() < Resource::PreloadReferencedWhileLoading)
844 imageMisses++;
845
846 if (res->errorOccurred())
847 memoryCache()->remove(res);
848
849 res->decreasePreloadCount();
850 }
851 m_preloads.clear();
852
853 if (scripts)
854 printf("SCRIPTS: %d (%d hits, hit rate %d%%)\n", scripts, scripts - scri ptMisses, (scripts - scriptMisses) * 100 / scripts);
855 if (stylesheets)
856 printf("STYLESHEETS: %d (%d hits, hit rate %d%%)\n", stylesheets, styles heets - stylesheetMisses, (stylesheets - stylesheetMisses) * 100 / stylesheets);
857 if (images)
858 printf("IMAGES: %d (%d hits, hit rate %d%%)\n", images, images - imageM isses, (images - imageMisses) * 100 / images);
859 }
860 #endif
861
862 const ResourceLoaderOptions& ResourceFetcher::defaultResourceOptions() 732 const ResourceLoaderOptions& ResourceFetcher::defaultResourceOptions()
863 { 733 {
864 DEFINE_STATIC_LOCAL(ResourceLoaderOptions, options, (BufferData, AllowStored Credentials, ClientRequestedCredentials, DocumentContext)); 734 DEFINE_STATIC_LOCAL(ResourceLoaderOptions, options, (BufferData, AllowStored Credentials, ClientRequestedCredentials, DocumentContext));
865 return options; 735 return options;
866 } 736 }
867 737
868 ResourceFetcher::DeadResourceStatsRecorder::DeadResourceStatsRecorder() 738 ResourceFetcher::DeadResourceStatsRecorder::DeadResourceStatsRecorder()
869 : m_useCount(0) 739 : m_useCount(0)
870 , m_revalidateCount(0) 740 , m_revalidateCount(0)
871 , m_loadCount(0) 741 , m_loadCount(0)
(...skipping 20 matching lines...) Expand all
892 case Revalidate: 762 case Revalidate:
893 ++m_revalidateCount; 763 ++m_revalidateCount;
894 return; 764 return;
895 case Use: 765 case Use:
896 ++m_useCount; 766 ++m_useCount;
897 return; 767 return;
898 } 768 }
899 } 769 }
900 770
901 } 771 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698