1/* 2 * Copyright (C) 2010 Apple Inc. All Rights Reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY APPLE, INC. ``AS IS'' AND ANY 14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR 17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 * 25 */ 26#include "config.h" 27#include "SchemeRegistry.h" 28#include <wtf/MainThread.h> 29 30namespace WebCore { 31 32static URLSchemesMap& localURLSchemes() 33{ 34 DEFINE_STATIC_LOCAL(URLSchemesMap, localSchemes, ()); 35 36 if (localSchemes.isEmpty()) { 37 localSchemes.add("file"); 38#if PLATFORM(MAC) 39 localSchemes.add("applewebdata"); 40#endif 41#if PLATFORM(QT) 42 localSchemes.add("qrc"); 43#endif 44 } 45 46 return localSchemes; 47} 48 49static URLSchemesMap& displayIsolatedURLSchemes() 50{ 51 DEFINE_STATIC_LOCAL(URLSchemesMap, displayIsolatedSchemes, ()); 52 return displayIsolatedSchemes; 53} 54 55static URLSchemesMap& secureSchemes() 56{ 57 DEFINE_STATIC_LOCAL(URLSchemesMap, secureSchemes, ()); 58 59 if (secureSchemes.isEmpty()) { 60 secureSchemes.add("https"); 61 secureSchemes.add("about"); 62 secureSchemes.add("data"); 63 } 64 65 return secureSchemes; 66} 67 68static URLSchemesMap& schemesWithUniqueOrigins() 69{ 70 DEFINE_STATIC_LOCAL(URLSchemesMap, schemesWithUniqueOrigins, ()); 71 72 if (schemesWithUniqueOrigins.isEmpty()) { 73 schemesWithUniqueOrigins.add("about"); 74 schemesWithUniqueOrigins.add("javascript"); 75 // This is a willful violation of HTML5. 76 // See https://bugs.webkit.org/show_bug.cgi?id=11885 77 schemesWithUniqueOrigins.add("data"); 78 } 79 80 return schemesWithUniqueOrigins; 81} 82 83static URLSchemesMap& emptyDocumentSchemes() 84{ 85 DEFINE_STATIC_LOCAL(URLSchemesMap, emptyDocumentSchemes, ()); 86 87 if (emptyDocumentSchemes.isEmpty()) 88 emptyDocumentSchemes.add("about"); 89 90 return emptyDocumentSchemes; 91} 92 93static HashSet<String>& schemesForbiddenFromDomainRelaxation() 94{ 95 DEFINE_STATIC_LOCAL(HashSet<String>, schemes, ()); 96 return schemes; 97} 98 99static URLSchemesMap& canDisplayOnlyIfCanRequestSchemes() 100{ 101 DEFINE_STATIC_LOCAL(URLSchemesMap, canDisplayOnlyIfCanRequestSchemes, ()); 102 103#if ENABLE(BLOB) 104 if (canDisplayOnlyIfCanRequestSchemes.isEmpty()) { 105 canDisplayOnlyIfCanRequestSchemes.add("blob"); 106#if ENABLE(FILE_SYSTEM) 107 canDisplayOnlyIfCanRequestSchemes.add("filesystem"); 108#endif 109 } 110#endif // ENABLE(BLOB) 111 112 return canDisplayOnlyIfCanRequestSchemes; 113} 114 115static URLSchemesMap& notAllowingJavascriptURLsSchemes() 116{ 117 DEFINE_STATIC_LOCAL(URLSchemesMap, notAllowingJavascriptURLsSchemes, ()); 118 return notAllowingJavascriptURLsSchemes; 119} 120 121void SchemeRegistry::registerURLSchemeAsLocal(const String& scheme) 122{ 123 localURLSchemes().add(scheme); 124} 125 126void SchemeRegistry::removeURLSchemeRegisteredAsLocal(const String& scheme) 127{ 128 if (scheme == "file") 129 return; 130#if PLATFORM(MAC) 131 if (scheme == "applewebdata") 132 return; 133#endif 134 localURLSchemes().remove(scheme); 135} 136 137const URLSchemesMap& SchemeRegistry::localSchemes() 138{ 139 return localURLSchemes(); 140} 141 142static URLSchemesMap& schemesAllowingLocalStorageAccessInPrivateBrowsing() 143{ 144 DEFINE_STATIC_LOCAL(URLSchemesMap, schemesAllowingLocalStorageAccessInPrivateBrowsing, ()); 145 return schemesAllowingLocalStorageAccessInPrivateBrowsing; 146} 147 148static URLSchemesMap& schemesAllowingDatabaseAccessInPrivateBrowsing() 149{ 150 DEFINE_STATIC_LOCAL(URLSchemesMap, schemesAllowingDatabaseAccessInPrivateBrowsing, ()); 151 return schemesAllowingDatabaseAccessInPrivateBrowsing; 152} 153 154static URLSchemesMap& CORSEnabledSchemes() 155{ 156 // FIXME: http://bugs.webkit.org/show_bug.cgi?id=77160 157 DEFINE_STATIC_LOCAL(URLSchemesMap, CORSEnabledSchemes, ()); 158 159 if (CORSEnabledSchemes.isEmpty()) { 160 CORSEnabledSchemes.add("http"); 161 CORSEnabledSchemes.add("https"); 162 } 163 164 return CORSEnabledSchemes; 165} 166 167static URLSchemesMap& ContentSecurityPolicyBypassingSchemes() 168{ 169 DEFINE_STATIC_LOCAL(URLSchemesMap, schemes, ()); 170 return schemes; 171} 172 173bool SchemeRegistry::shouldTreatURLSchemeAsLocal(const String& scheme) 174{ 175 if (scheme.isEmpty()) 176 return false; 177 return localURLSchemes().contains(scheme); 178} 179 180void SchemeRegistry::registerURLSchemeAsNoAccess(const String& scheme) 181{ 182 schemesWithUniqueOrigins().add(scheme); 183} 184 185bool SchemeRegistry::shouldTreatURLSchemeAsNoAccess(const String& scheme) 186{ 187 if (scheme.isEmpty()) 188 return false; 189 return schemesWithUniqueOrigins().contains(scheme); 190} 191 192void SchemeRegistry::registerURLSchemeAsDisplayIsolated(const String& scheme) 193{ 194 displayIsolatedURLSchemes().add(scheme); 195} 196 197bool SchemeRegistry::shouldTreatURLSchemeAsDisplayIsolated(const String& scheme) 198{ 199 if (scheme.isEmpty()) 200 return false; 201 return displayIsolatedURLSchemes().contains(scheme); 202} 203 204void SchemeRegistry::registerURLSchemeAsSecure(const String& scheme) 205{ 206 secureSchemes().add(scheme); 207} 208 209bool SchemeRegistry::shouldTreatURLSchemeAsSecure(const String& scheme) 210{ 211 if (scheme.isEmpty()) 212 return false; 213 return secureSchemes().contains(scheme); 214} 215 216void SchemeRegistry::registerURLSchemeAsEmptyDocument(const String& scheme) 217{ 218 emptyDocumentSchemes().add(scheme); 219} 220 221bool SchemeRegistry::shouldLoadURLSchemeAsEmptyDocument(const String& scheme) 222{ 223 if (scheme.isEmpty()) 224 return false; 225 return emptyDocumentSchemes().contains(scheme); 226} 227 228void SchemeRegistry::setDomainRelaxationForbiddenForURLScheme(bool forbidden, const String& scheme) 229{ 230 if (scheme.isEmpty()) 231 return; 232 233 if (forbidden) 234 schemesForbiddenFromDomainRelaxation().add(scheme); 235 else 236 schemesForbiddenFromDomainRelaxation().remove(scheme); 237} 238 239bool SchemeRegistry::isDomainRelaxationForbiddenForURLScheme(const String& scheme) 240{ 241 if (scheme.isEmpty()) 242 return false; 243 return schemesForbiddenFromDomainRelaxation().contains(scheme); 244} 245 246bool SchemeRegistry::canDisplayOnlyIfCanRequest(const String& scheme) 247{ 248 if (scheme.isEmpty()) 249 return false; 250 return canDisplayOnlyIfCanRequestSchemes().contains(scheme); 251} 252 253void SchemeRegistry::registerAsCanDisplayOnlyIfCanRequest(const String& scheme) 254{ 255 canDisplayOnlyIfCanRequestSchemes().add(scheme); 256} 257 258void SchemeRegistry::registerURLSchemeAsNotAllowingJavascriptURLs(const String& scheme) 259{ 260 notAllowingJavascriptURLsSchemes().add(scheme); 261} 262 263bool SchemeRegistry::shouldTreatURLSchemeAsNotAllowingJavascriptURLs(const String& scheme) 264{ 265 if (scheme.isEmpty()) 266 return false; 267 return notAllowingJavascriptURLsSchemes().contains(scheme); 268} 269 270void SchemeRegistry::registerURLSchemeAsAllowingLocalStorageAccessInPrivateBrowsing(const String& scheme) 271{ 272 schemesAllowingLocalStorageAccessInPrivateBrowsing().add(scheme); 273} 274 275bool SchemeRegistry::allowsLocalStorageAccessInPrivateBrowsing(const String& scheme) 276{ 277 if (scheme.isEmpty()) 278 return false; 279 return schemesAllowingLocalStorageAccessInPrivateBrowsing().contains(scheme); 280} 281 282void SchemeRegistry::registerURLSchemeAsAllowingDatabaseAccessInPrivateBrowsing(const String& scheme) 283{ 284 schemesAllowingDatabaseAccessInPrivateBrowsing().add(scheme); 285} 286 287bool SchemeRegistry::allowsDatabaseAccessInPrivateBrowsing(const String& scheme) 288{ 289 if (scheme.isEmpty()) 290 return false; 291 return schemesAllowingDatabaseAccessInPrivateBrowsing().contains(scheme); 292} 293 294void SchemeRegistry::registerURLSchemeAsCORSEnabled(const String& scheme) 295{ 296 CORSEnabledSchemes().add(scheme); 297} 298 299bool SchemeRegistry::shouldTreatURLSchemeAsCORSEnabled(const String& scheme) 300{ 301 if (scheme.isEmpty()) 302 return false; 303 return CORSEnabledSchemes().contains(scheme); 304} 305 306void SchemeRegistry::registerURLSchemeAsBypassingContentSecurityPolicy(const String& scheme) 307{ 308 ContentSecurityPolicyBypassingSchemes().add(scheme); 309} 310 311void SchemeRegistry::removeURLSchemeRegisteredAsBypassingContentSecurityPolicy(const String& scheme) 312{ 313 ContentSecurityPolicyBypassingSchemes().remove(scheme); 314} 315 316bool SchemeRegistry::schemeShouldBypassContentSecurityPolicy(const String& scheme) 317{ 318 if (scheme.isEmpty()) 319 return false; 320 return ContentSecurityPolicyBypassingSchemes().contains(scheme); 321} 322 323bool SchemeRegistry::shouldCacheResponsesFromURLSchemeIndefinitely(const String& scheme) 324{ 325#if PLATFORM(MAC) 326 if (equalIgnoringCase(scheme, "applewebdata")) 327 return true; 328#endif 329 return equalIgnoringCase(scheme, "data"); 330} 331 332} // namespace WebCore 333