1 /* 2 Copyright (C) 1998 Lars Knoll (knoll (at) mpi-hd.mpg.de) 3 Copyright (C) 2001 Dirk Mueller <mueller (at) kde.org> 4 Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved. 5 Copyright (C) 2009 Torch Mobile Inc. http://www.torchmobile.com/ 6 7 This library is free software; you can redistribute it and/or 8 modify it under the terms of the GNU Library General Public 9 License as published by the Free Software Foundation; either 10 version 2 of the License, or (at your option) any later version. 11 12 This library is distributed in the hope that it will be useful, 13 but WITHOUT ANY WARRANTY; without even the implied warranty of 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 Library General Public License for more details. 16 17 You should have received a copy of the GNU Library General Public License 18 along with this library; see the file COPYING.LIB. If not, write to 19 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 20 Boston, MA 02110-1301, USA. 21 22 This class provides all functionality needed for loading images, style sheets and html 23 pages from the web. It has a memory cache for these objects. 24 */ 25 26 #ifndef ResourceFetcher_h 27 #define ResourceFetcher_h 28 29 #include "core/loader/ResourceLoaderHost.h" 30 #include "core/loader/cache/CachePolicy.h" 31 #include "core/loader/cache/FetchInitiatorInfo.h" 32 #include "core/loader/cache/FetchRequest.h" 33 #include "core/loader/cache/Resource.h" 34 #include "core/loader/cache/ResourcePtr.h" 35 #include "core/platform/Timer.h" 36 #include "wtf/Deque.h" 37 #include "wtf/HashMap.h" 38 #include "wtf/HashSet.h" 39 #include "wtf/ListHashSet.h" 40 #include "wtf/text/StringHash.h" 41 42 namespace WebCore { 43 44 class CSSStyleSheetResource; 45 class DocumentResource; 46 class FontResource; 47 class ImageResource; 48 class RawResource; 49 class ScriptResource; 50 class ShaderResource; 51 class TextTrackResource; 52 class XSLStyleSheetResource; 53 class Document; 54 class DocumentLoader; 55 class Frame; 56 class FrameLoader; 57 class ImageLoader; 58 class KURL; 59 class ResourceTimingInfo; 60 61 // The ResourceFetcher provides a per-context interface to the MemoryCache 62 // and enforces a bunch of security checks and rules for resource revalidation. 63 // Its lifetime is roughly per-DocumentLoader, in that it is generally created 64 // in the DocumentLoader constructor and loses its ability to generate network 65 // requests when the DocumentLoader is destroyed. Documents also hold a 66 // RefPtr<ResourceFetcher> for their lifetime (and will create one if they 67 // are initialized without a Frame), so a Document can keep a ResourceFetcher 68 // alive past detach if scripts still reference the Document. 69 class ResourceFetcher : public RefCounted<ResourceFetcher>, public ResourceLoaderHost { 70 WTF_MAKE_NONCOPYABLE(ResourceFetcher); WTF_MAKE_FAST_ALLOCATED; 71 friend class ImageLoader; 72 friend class ResourceCacheValidationSuppressor; 73 74 public: 75 static PassRefPtr<ResourceFetcher> create(DocumentLoader* documentLoader) { return adoptRef(new ResourceFetcher(documentLoader)); } 76 virtual ~ResourceFetcher(); 77 78 using RefCounted<ResourceFetcher>::ref; 79 using RefCounted<ResourceFetcher>::deref; 80 81 ResourcePtr<ImageResource> requestImage(FetchRequest&); 82 ResourcePtr<CSSStyleSheetResource> requestCSSStyleSheet(FetchRequest&); 83 ResourcePtr<CSSStyleSheetResource> requestUserCSSStyleSheet(FetchRequest&); 84 ResourcePtr<ScriptResource> requestScript(FetchRequest&); 85 ResourcePtr<FontResource> requestFont(FetchRequest&); 86 ResourcePtr<RawResource> requestRawResource(FetchRequest&); 87 ResourcePtr<RawResource> requestMainResource(FetchRequest&); 88 ResourcePtr<DocumentResource> requestSVGDocument(FetchRequest&); 89 ResourcePtr<XSLStyleSheetResource> requestXSLStyleSheet(FetchRequest&); 90 ResourcePtr<Resource> requestLinkResource(Resource::Type, FetchRequest&); 91 ResourcePtr<TextTrackResource> requestTextTrack(FetchRequest&); 92 ResourcePtr<ShaderResource> requestShader(FetchRequest&); 93 ResourcePtr<RawResource> requestImport(FetchRequest&); 94 95 // Logs an access denied message to the console for the specified URL. 96 void printAccessDeniedMessage(const KURL&) const; 97 98 Resource* cachedResource(const String& url) const; 99 Resource* cachedResource(const KURL&) const; 100 101 typedef HashMap<String, ResourcePtr<Resource> > DocumentResourceMap; 102 const DocumentResourceMap& allResources() const { return m_documentResources; } 103 104 bool autoLoadImages() const { return m_autoLoadImages; } 105 void setAutoLoadImages(bool); 106 107 void setImagesEnabled(bool); 108 109 bool shouldDeferImageLoad(const KURL&) const; 110 111 CachePolicy cachePolicy(Resource::Type) const; 112 113 Frame* frame() const; // Can be null 114 Document* document() const { return m_document; } // Can be null 115 void setDocument(Document* document) { m_document = document; } 116 117 DocumentLoader* documentLoader() const { return m_documentLoader; } 118 void clearDocumentLoader() { m_documentLoader = 0; } 119 120 void garbageCollectDocumentResources(); 121 122 int requestCount() const { return m_requestCount; } 123 124 bool isPreloaded(const String& urlString) const; 125 void clearPreloads(); 126 void clearPendingPreloads(); 127 void preload(Resource::Type, FetchRequest&, const String& charset); 128 void checkForPendingPreloads(); 129 void printPreloadStats(); 130 bool canRequest(Resource::Type, const KURL&, const ResourceLoaderOptions&, bool forPreload = false); 131 bool canAccess(Resource*); 132 133 // ResourceLoaderHost 134 virtual void incrementRequestCount(const Resource*) OVERRIDE; 135 virtual void decrementRequestCount(const Resource*) OVERRIDE; 136 virtual void didLoadResource(Resource*) OVERRIDE; 137 virtual void redirectReceived(Resource*, const ResourceResponse&) OVERRIDE; 138 virtual void didFinishLoading(const Resource*, double finishTime, const ResourceLoaderOptions&) OVERRIDE; 139 virtual void didChangeLoadingPriority(const Resource*, ResourceLoadPriority) OVERRIDE; 140 virtual void didFailLoading(const Resource*, const ResourceError&, const ResourceLoaderOptions&) OVERRIDE; 141 virtual void willSendRequest(const Resource*, ResourceRequest&, const ResourceResponse& redirectResponse, const ResourceLoaderOptions&) OVERRIDE; 142 virtual void didReceiveResponse(const Resource*, const ResourceResponse&, const ResourceLoaderOptions&) OVERRIDE; 143 virtual void didReceiveData(const Resource*, const char* data, int dataLength, int encodedDataLength, const ResourceLoaderOptions&) OVERRIDE; 144 virtual void subresourceLoaderFinishedLoadingOnePart(ResourceLoader*) OVERRIDE; 145 virtual void didInitializeResourceLoader(ResourceLoader*) OVERRIDE; 146 virtual void willTerminateResourceLoader(ResourceLoader*) OVERRIDE; 147 virtual void willStartLoadingResource(ResourceRequest&) OVERRIDE; 148 virtual bool defersLoading() const OVERRIDE; 149 virtual bool isLoadedBy(ResourceLoaderHost*) const OVERRIDE; 150 virtual bool shouldRequest(Resource*, const ResourceRequest&, const ResourceLoaderOptions&) OVERRIDE; 151 virtual void refResourceLoaderHost() OVERRIDE; 152 virtual void derefResourceLoaderHost() OVERRIDE; 153 154 static const ResourceLoaderOptions& defaultResourceOptions(); 155 private: 156 157 explicit ResourceFetcher(DocumentLoader*); 158 159 FrameLoader* frameLoader(); 160 bool shouldLoadNewResource() const; 161 162 ResourcePtr<Resource> requestResource(Resource::Type, FetchRequest&); 163 ResourcePtr<Resource> revalidateResource(const FetchRequest&, Resource*); 164 ResourcePtr<Resource> loadResource(Resource::Type, FetchRequest&, const String& charset); 165 void preCacheDataURIImage(const FetchRequest&); 166 void storeResourceTimingInitiatorInformation(const ResourcePtr<Resource>&, const FetchRequest&); 167 void requestPreload(Resource::Type, FetchRequest&, const String& charset); 168 169 enum RevalidationPolicy { Use, Revalidate, Reload, Load }; 170 RevalidationPolicy determineRevalidationPolicy(Resource::Type, ResourceRequest&, bool forPreload, Resource* existingResource, FetchRequest::DeferOption) const; 171 172 void determineTargetType(ResourceRequest&, Resource::Type); 173 ResourceRequestCachePolicy resourceRequestCachePolicy(const ResourceRequest&, Resource::Type); 174 void addAdditionalRequestHeaders(ResourceRequest&, Resource::Type); 175 176 void notifyLoadedFromMemoryCache(Resource*); 177 bool checkInsecureContent(Resource::Type, const KURL&) const; 178 179 void garbageCollectDocumentResourcesTimerFired(Timer<ResourceFetcher>*); 180 void performPostLoadActions(); 181 182 bool clientDefersImage(const KURL&) const; 183 void reloadImagesIfNotDeferred(); 184 185 HashSet<String> m_validatedURLs; 186 mutable DocumentResourceMap m_documentResources; 187 Document* m_document; 188 DocumentLoader* m_documentLoader; 189 190 int m_requestCount; 191 192 OwnPtr<ListHashSet<Resource*> > m_preloads; 193 struct PendingPreload { 194 Resource::Type m_type; 195 FetchRequest m_request; 196 String m_charset; 197 }; 198 Deque<PendingPreload> m_pendingPreloads; 199 200 Timer<ResourceFetcher> m_garbageCollectDocumentResourcesTimer; 201 202 typedef HashMap<Resource*, RefPtr<ResourceTimingInfo> > ResourceTimingInfoMap; 203 ResourceTimingInfoMap m_resourceTimingInfoMap; 204 205 // 29 bits left 206 bool m_autoLoadImages : 1; 207 bool m_imagesEnabled : 1; 208 bool m_allowStaleResources : 1; 209 }; 210 211 class ResourceCacheValidationSuppressor { 212 WTF_MAKE_NONCOPYABLE(ResourceCacheValidationSuppressor); 213 WTF_MAKE_FAST_ALLOCATED; 214 public: 215 ResourceCacheValidationSuppressor(ResourceFetcher* loader) 216 : m_loader(loader) 217 , m_previousState(false) 218 { 219 if (m_loader) { 220 m_previousState = m_loader->m_allowStaleResources; 221 m_loader->m_allowStaleResources = true; 222 } 223 } 224 ~ResourceCacheValidationSuppressor() 225 { 226 if (m_loader) 227 m_loader->m_allowStaleResources = m_previousState; 228 } 229 private: 230 ResourceFetcher* m_loader; 231 bool m_previousState; 232 }; 233 234 } // namespace WebCore 235 236 #endif 237