Make _WKWebsiteDataStoreConfiguration SPI for HSTS storage to replace _WKProcessPoolC...
authorcommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 30 Jun 2020 04:39:50 +0000 (04:39 +0000)
committercommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 30 Jun 2020 04:39:50 +0000 (04:39 +0000)
https://bugs.webkit.org/show_bug.cgi?id=213048

Patch by Alex Christensen <achristensen@webkit.org> on 2020-06-29
Reviewed by Youenn Fablet.

Source/WebCore/PAL:

* pal/spi/cf/CFNetworkSPI.h:

Source/WebKit:

This uses CFNetwork SPI introduced in rdar://problem/50109631 to allow HSTS storage per NSURLSession.
To be complete, I also deprecated our UI process HSTS state removal attempt SPIs, WKContextResetHSTSHosts and
WKContextResetHSTSHostsAddedAfterDate, which had their last use removed in rdar://problem/64220838.

I manually verified that this new SPI puts HSTS data in the specified location, and I also verified that HSTS
state querying and removal works with the new CFNetwork SPI as it did with the old one.

* NetworkProcess/NetworkProcess.cpp:
(WebKit::NetworkProcess::fetchWebsiteData):
(WebKit::NetworkProcess::deleteWebsiteData):
(WebKit::NetworkProcess::deleteWebsiteDataForOrigins):
(WebKit::NetworkProcess::deleteAndRestrictWebsiteDataForRegistrableDomains):
(WebKit::NetworkProcess::registrableDomainsWithWebsiteData):
* NetworkProcess/NetworkProcess.h:
* NetworkProcess/NetworkSessionCreationParameters.cpp:
(WebKit::NetworkSessionCreationParameters::encode const):
(WebKit::NetworkSessionCreationParameters::decode):
* NetworkProcess/NetworkSessionCreationParameters.h:
* NetworkProcess/cocoa/NetworkProcessCocoa.mm:
(WebKit::NetworkProcess::hostNamesWithHSTSCache const):
(WebKit::NetworkProcess::deleteHSTSCacheForHostNames):
(WebKit::NetworkProcess::clearHSTSCache):
(WebKit::NetworkProcess::getHostNamesWithHSTSCache): Deleted.
* NetworkProcess/cocoa/NetworkSessionCocoa.h:
* NetworkProcess/cocoa/NetworkSessionCocoa.mm:
(WebKit::NetworkSessionCocoa::hstsStorage const):
(WebKit::NetworkSessionCocoa::NetworkSessionCocoa):
* NetworkProcess/soup/NetworkProcessSoup.cpp:
(WebKit::NetworkProcess::hostNamesWithHSTSCache const):
(WebKit::NetworkProcess::deleteHSTSCacheForHostNames):
(WebKit::NetworkProcess::clearHSTSCache):
(WebKit::NetworkProcess::getHostNamesWithHSTSCache): Deleted.
* UIProcess/API/C/mac/WKContextPrivateMac.h:
* UIProcess/API/C/mac/WKContextPrivateMac.mm:
(WKContextResetHSTSHosts):
(WKContextResetHSTSHostsAddedAfterDate):
* UIProcess/API/Cocoa/_WKProcessPoolConfiguration.h:
* UIProcess/API/Cocoa/_WKWebsiteDataStoreConfiguration.h:
* UIProcess/API/Cocoa/_WKWebsiteDataStoreConfiguration.mm:
(-[_WKWebsiteDataStoreConfiguration hstsStorageDirectory]):
(-[_WKWebsiteDataStoreConfiguration setHSTSStorageDirectory:]):
* UIProcess/Cocoa/WebProcessPoolCocoa.mm:
(WebKit::privateBrowsingSession): Deleted.
(WebKit::WebProcessPool::resetHSTSHosts): Deleted.
(WebKit::WebProcessPool::resetHSTSHostsAddedAfterDate): Deleted.
* UIProcess/WebProcessPool.h:
* UIProcess/WebsiteData/WebsiteDataStore.cpp:
(WebKit::WebsiteDataStore::resolveDirectoriesIfNecessary):
(WebKit::WebsiteDataStore::parameters):
* UIProcess/WebsiteData/WebsiteDataStore.h:
(WebKit::WebsiteDataStore::resolvedHSTSStorageDirectory const):
* UIProcess/WebsiteData/WebsiteDataStoreConfiguration.cpp:
(WebKit::WebsiteDataStoreConfiguration::copy const):
* UIProcess/WebsiteData/WebsiteDataStoreConfiguration.h:

Source/WTF:

* wtf/PlatformHave.h:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@263724 268f45cc-cd09-0410-ab3c-d52691b4dbfc

24 files changed:
Source/WTF/ChangeLog
Source/WTF/wtf/PlatformHave.h
Source/WebCore/PAL/ChangeLog
Source/WebCore/PAL/pal/spi/cf/CFNetworkSPI.h
Source/WebKit/ChangeLog
Source/WebKit/NetworkProcess/NetworkProcess.cpp
Source/WebKit/NetworkProcess/NetworkProcess.h
Source/WebKit/NetworkProcess/NetworkSessionCreationParameters.cpp
Source/WebKit/NetworkProcess/NetworkSessionCreationParameters.h
Source/WebKit/NetworkProcess/cocoa/NetworkProcessCocoa.mm
Source/WebKit/NetworkProcess/cocoa/NetworkSessionCocoa.h
Source/WebKit/NetworkProcess/cocoa/NetworkSessionCocoa.mm
Source/WebKit/NetworkProcess/soup/NetworkProcessSoup.cpp
Source/WebKit/UIProcess/API/C/mac/WKContextPrivateMac.h
Source/WebKit/UIProcess/API/C/mac/WKContextPrivateMac.mm
Source/WebKit/UIProcess/API/Cocoa/_WKProcessPoolConfiguration.h
Source/WebKit/UIProcess/API/Cocoa/_WKWebsiteDataStoreConfiguration.h
Source/WebKit/UIProcess/API/Cocoa/_WKWebsiteDataStoreConfiguration.mm
Source/WebKit/UIProcess/Cocoa/WebProcessPoolCocoa.mm
Source/WebKit/UIProcess/WebProcessPool.h
Source/WebKit/UIProcess/WebsiteData/WebsiteDataStore.cpp
Source/WebKit/UIProcess/WebsiteData/WebsiteDataStore.h
Source/WebKit/UIProcess/WebsiteData/WebsiteDataStoreConfiguration.cpp
Source/WebKit/UIProcess/WebsiteData/WebsiteDataStoreConfiguration.h

index 9c62ed0..0429f35 100644 (file)
@@ -1,3 +1,12 @@
+2020-06-29  Alex Christensen  <achristensen@webkit.org>
+
+        Make _WKWebsiteDataStoreConfiguration SPI for HSTS storage to replace _WKProcessPoolConfiguration.hstsStorageDirectory
+        https://bugs.webkit.org/show_bug.cgi?id=213048
+
+        Reviewed by Youenn Fablet.
+
+        * wtf/PlatformHave.h:
+
 2020-06-29  Geoffrey Garen  <ggaren@apple.com>
 
         [GTK] [Win] Build callOnMainThread on WTF::RunLoop rather than on a timer
index 48c0df3..1f4bc4a 100644 (file)
 #define HAVE_BROKEN_DOWNLOAD_RESUME_UNLINK 1
 #endif
 
+#if (PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101600) \
+    || ((PLATFORM(IOS) || PLATFORM(MACCATALYST)) && __IPHONE_OS_VERSION_MIN_REQUIRED >= 140000) \
+    || (PLATFORM(WATCHOS) && __WATCH_OS_VERSION_MIN_REQUIRED >= 70000) \
+    || (PLATFORM(APPLETV) && __TV_OS_VERSION_MIN_REQUIRED >= 140000)
+#define HAVE_HSTS_STORAGE 1
+#endif
+
 #if (PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101600) || (PLATFORM(IOS_FAMILY) && __IPHONE_OS_VERSION_MIN_REQUIRED >= 140000)
 #define HAVE_CFNETWORK_METRICS_APIS_V4 1
 #endif
index 27077f6..a4ee50f 100644 (file)
@@ -1,3 +1,12 @@
+2020-06-29  Alex Christensen  <achristensen@webkit.org>
+
+        Make _WKWebsiteDataStoreConfiguration SPI for HSTS storage to replace _WKProcessPoolConfiguration.hstsStorageDirectory
+        https://bugs.webkit.org/show_bug.cgi?id=213048
+
+        Reviewed by Youenn Fablet.
+
+        * pal/spi/cf/CFNetworkSPI.h:
+
 2020-06-29  Tetsuharu Ohzeki  <tetsuharu.ohzeki@gmail.com>
 
         Remove ENABLE_STREAMS_API compilation flag
index 6570fb9..b8c467f 100644 (file)
@@ -407,7 +407,7 @@ WTF_EXTERN_C_BEGIN
 CFDataRef _CFNetworkCopyATSContext(void);
 Boolean _CFNetworkSetATSContext(CFDataRef);
 
-#if PLATFORM(COCOA)
+#if PLATFORM(COCOA) && !HAVE(HSTS_STORAGE)
 extern const CFStringRef _kCFNetworkHSTSPreloaded;
 CFDictionaryRef _CFNetworkCopyHSTSPolicies(CFURLStorageSessionRef);
 void _CFNetworkResetHSTS(CFURLRef, CFURLStorageSessionRef);
@@ -458,9 +458,22 @@ WTF_EXTERN_C_END
 - (void)_setMIMEType:(NSString *)type;
 @end
 
+#if HAVE(HSTS_STORAGE)
+@interface _NSHSTSStorage : NSObject
+-(instancetype)initPersistentStoreWithURL:(nullable NSURL*)path;
+-(BOOL)shouldPromoteHostToHTTPS:(NSString *)host;
+-(NSArray<NSString *> *)nonPreloadedHosts;
+-(void)resetHSTSForHost:(NSString *)host;
+-(void)resetHSTSHostsSinceDate:(NSDate *)date;
+@end
+#endif
+
 @interface NSURLSessionConfiguration ()
 // FIXME: Remove this once rdar://problem/40650244 is in a build.
 @property (copy) NSDictionary *_socketStreamProperties;
+#if HAVE(HSTS_STORAGE)
+@property (nullable, retain) _NSHSTSStorage *_hstsStorage;
+#endif
 @end
 
 @interface NSURLSessionTask ()
index 77dcd11..1c2f3a7 100644 (file)
@@ -1,3 +1,65 @@
+2020-06-29  Alex Christensen  <achristensen@webkit.org>
+
+        Make _WKWebsiteDataStoreConfiguration SPI for HSTS storage to replace _WKProcessPoolConfiguration.hstsStorageDirectory
+        https://bugs.webkit.org/show_bug.cgi?id=213048
+
+        Reviewed by Youenn Fablet.
+
+        This uses CFNetwork SPI introduced in rdar://problem/50109631 to allow HSTS storage per NSURLSession.
+        To be complete, I also deprecated our UI process HSTS state removal attempt SPIs, WKContextResetHSTSHosts and
+        WKContextResetHSTSHostsAddedAfterDate, which had their last use removed in rdar://problem/64220838.
+
+        I manually verified that this new SPI puts HSTS data in the specified location, and I also verified that HSTS
+        state querying and removal works with the new CFNetwork SPI as it did with the old one.
+
+        * NetworkProcess/NetworkProcess.cpp:
+        (WebKit::NetworkProcess::fetchWebsiteData):
+        (WebKit::NetworkProcess::deleteWebsiteData):
+        (WebKit::NetworkProcess::deleteWebsiteDataForOrigins):
+        (WebKit::NetworkProcess::deleteAndRestrictWebsiteDataForRegistrableDomains):
+        (WebKit::NetworkProcess::registrableDomainsWithWebsiteData):
+        * NetworkProcess/NetworkProcess.h:
+        * NetworkProcess/NetworkSessionCreationParameters.cpp:
+        (WebKit::NetworkSessionCreationParameters::encode const):
+        (WebKit::NetworkSessionCreationParameters::decode):
+        * NetworkProcess/NetworkSessionCreationParameters.h:
+        * NetworkProcess/cocoa/NetworkProcessCocoa.mm:
+        (WebKit::NetworkProcess::hostNamesWithHSTSCache const):
+        (WebKit::NetworkProcess::deleteHSTSCacheForHostNames):
+        (WebKit::NetworkProcess::clearHSTSCache):
+        (WebKit::NetworkProcess::getHostNamesWithHSTSCache): Deleted.
+        * NetworkProcess/cocoa/NetworkSessionCocoa.h:
+        * NetworkProcess/cocoa/NetworkSessionCocoa.mm:
+        (WebKit::NetworkSessionCocoa::hstsStorage const):
+        (WebKit::NetworkSessionCocoa::NetworkSessionCocoa):
+        * NetworkProcess/soup/NetworkProcessSoup.cpp:
+        (WebKit::NetworkProcess::hostNamesWithHSTSCache const):
+        (WebKit::NetworkProcess::deleteHSTSCacheForHostNames):
+        (WebKit::NetworkProcess::clearHSTSCache):
+        (WebKit::NetworkProcess::getHostNamesWithHSTSCache): Deleted.
+        * UIProcess/API/C/mac/WKContextPrivateMac.h:
+        * UIProcess/API/C/mac/WKContextPrivateMac.mm:
+        (WKContextResetHSTSHosts):
+        (WKContextResetHSTSHostsAddedAfterDate):
+        * UIProcess/API/Cocoa/_WKProcessPoolConfiguration.h:
+        * UIProcess/API/Cocoa/_WKWebsiteDataStoreConfiguration.h:
+        * UIProcess/API/Cocoa/_WKWebsiteDataStoreConfiguration.mm:
+        (-[_WKWebsiteDataStoreConfiguration hstsStorageDirectory]):
+        (-[_WKWebsiteDataStoreConfiguration setHSTSStorageDirectory:]):
+        * UIProcess/Cocoa/WebProcessPoolCocoa.mm:
+        (WebKit::privateBrowsingSession): Deleted.
+        (WebKit::WebProcessPool::resetHSTSHosts): Deleted.
+        (WebKit::WebProcessPool::resetHSTSHostsAddedAfterDate): Deleted.
+        * UIProcess/WebProcessPool.h:
+        * UIProcess/WebsiteData/WebsiteDataStore.cpp:
+        (WebKit::WebsiteDataStore::resolveDirectoriesIfNecessary):
+        (WebKit::WebsiteDataStore::parameters):
+        * UIProcess/WebsiteData/WebsiteDataStore.h:
+        (WebKit::WebsiteDataStore::resolvedHSTSStorageDirectory const):
+        * UIProcess/WebsiteData/WebsiteDataStoreConfiguration.cpp:
+        (WebKit::WebsiteDataStoreConfiguration::copy const):
+        * UIProcess/WebsiteData/WebsiteDataStoreConfiguration.h:
+
 2020-06-29  Tim Horton  <timothy_horton@apple.com>
 
         Adopt adjusted symbol image names
index f123b20..9daf226 100644 (file)
@@ -1534,10 +1534,8 @@ void NetworkProcess::fetchWebsiteData(PAL::SessionID sessionID, OptionSet<Websit
     }
 
 #if PLATFORM(COCOA) || USE(SOUP)
-    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache)) {
-        if (auto* networkStorageSession = storageSession(sessionID))
-            getHostNamesWithHSTSCache(*networkStorageSession, callbackAggregator->m_websiteData.hostNamesWithHSTSCache);
-    }
+    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache))
+        callbackAggregator->m_websiteData.hostNamesWithHSTSCache = hostNamesWithHSTSCache(sessionID);
 #endif
 
 #if ENABLE(INDEXED_DATABASE)
@@ -1596,10 +1594,8 @@ void NetworkProcess::fetchWebsiteData(PAL::SessionID sessionID, OptionSet<Websit
 void NetworkProcess::deleteWebsiteData(PAL::SessionID sessionID, OptionSet<WebsiteDataType> websiteDataTypes, WallTime modifiedSince, CallbackID callbackID)
 {
 #if PLATFORM(COCOA) || USE(SOUP)
-    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache)) {
-        if (auto* networkStorageSession = storageSession(sessionID))
-            clearHSTSCache(*networkStorageSession, modifiedSince);
-    }
+    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache))
+        clearHSTSCache(sessionID, modifiedSince);
 #endif
 
     if (websiteDataTypes.contains(WebsiteDataType::Cookies)) {
@@ -1701,10 +1697,8 @@ void NetworkProcess::deleteWebsiteDataForOrigins(PAL::SessionID sessionID, Optio
     }
 
 #if PLATFORM(COCOA) || USE(SOUP)
-    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache)) {
-        if (auto* networkStorageSession = storageSession(sessionID))
-            deleteHSTSCacheForHostNames(*networkStorageSession, HSTSCacheHostNames);
-    }
+    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache))
+        deleteHSTSCacheForHostNames(sessionID, HSTSCacheHostNames);
 #endif
 
 #if HAVE(CFNETWORK_ALTERNATIVE_SERVICE)
@@ -1872,15 +1866,13 @@ void NetworkProcess::deleteAndRestrictWebsiteDataForRegistrableDomains(PAL::Sess
     Vector<String> hostnamesWithHSTSToDelete;
 #if PLATFORM(COCOA) || USE(SOUP)
     if (websiteDataTypes.contains(WebsiteDataType::HSTSCache)) {
-        if (auto* networkStorageSession = storageSession(sessionID)) {
-            getHostNamesWithHSTSCache(*networkStorageSession, hostNamesWithHSTSCache);
-            hostnamesWithHSTSToDelete = filterForRegistrableDomains(domainsToDeleteAllNonCookieWebsiteDataFor, hostNamesWithHSTSCache);
+        hostNamesWithHSTSCache = this->hostNamesWithHSTSCache(sessionID);
+        hostnamesWithHSTSToDelete = filterForRegistrableDomains(domainsToDeleteAllNonCookieWebsiteDataFor, hostNamesWithHSTSCache);
 
-            for (const auto& host : hostnamesWithHSTSToDelete)
-                callbackAggregator->m_domains.add(RegistrableDomain::uncheckedCreateFromHost(host));
+        for (const auto& host : hostnamesWithHSTSToDelete)
+            callbackAggregator->m_domains.add(RegistrableDomain::uncheckedCreateFromHost(host));
 
-            deleteHSTSCacheForHostNames(*networkStorageSession, hostnamesWithHSTSToDelete);
-        }
+        deleteHSTSCacheForHostNames(sessionID, hostnamesWithHSTSToDelete);
     }
 #endif
 
@@ -2057,18 +2049,16 @@ void NetworkProcess::registrableDomainsWithWebsiteData(PAL::SessionID sessionID,
         });
     }));
     
-    auto& websiteDataStore = callbackAggregator->m_websiteData;
+    auto& websiteData = callbackAggregator->m_websiteData;
     
     if (websiteDataTypes.contains(WebsiteDataType::Cookies)) {
         if (auto* networkStorageSession = storageSession(sessionID))
-            networkStorageSession->getHostnamesWithCookies(websiteDataStore.hostNamesWithCookies);
+            networkStorageSession->getHostnamesWithCookies(websiteData.hostNamesWithCookies);
     }
     
 #if PLATFORM(COCOA) || USE(SOUP)
-    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache)) {
-        if (auto* networkStorageSession = storageSession(sessionID))
-            getHostNamesWithHSTSCache(*networkStorageSession, websiteDataStore.hostNamesWithHSTSCache);
-    }
+    if (websiteDataTypes.contains(WebsiteDataType::HSTSCache))
+        websiteData.hostNamesWithHSTSCache = hostNamesWithHSTSCache(sessionID);
 #endif
 
     if (websiteDataTypes.contains(WebsiteDataType::Credentials)) {
index 7fb9f7b..3239c4b 100644 (file)
@@ -193,9 +193,9 @@ public:
     RetainPtr<CFDataRef> sourceApplicationAuditData() const;
 #endif
 #if PLATFORM(COCOA) || USE(SOUP)
-    void getHostNamesWithHSTSCache(WebCore::NetworkStorageSession&, HashSet<String>&);
-    void deleteHSTSCacheForHostNames(WebCore::NetworkStorageSession&, const Vector<String>&);
-    void clearHSTSCache(WebCore::NetworkStorageSession&, WallTime modifiedSince);
+    HashSet<String> hostNamesWithHSTSCache(PAL::SessionID) const;
+    void deleteHSTSCacheForHostNames(PAL::SessionID, const Vector<String>&);
+    void clearHSTSCache(PAL::SessionID, WallTime modifiedSince);
 #endif
 
     void findPendingDownloadLocation(NetworkDataTask&, ResponseCompletionHandler&&, const WebCore::ResourceResponse&);
index 3d83cd2..e2edbce 100644 (file)
@@ -57,6 +57,8 @@ void NetworkSessionCreationParameters::encode(IPC::Encoder& encoder) const
     encoder << alternativeServiceDirectoryExtensionHandle;
     encoder << http3Enabled;
 #endif
+    encoder << hstsStorageDirectory;
+    encoder << hstsStorageDirectoryExtensionHandle;
 #if USE(SOUP)
     encoder << cookiePersistentStoragePath;
     encoder << cookiePersistentStorageType;
@@ -153,6 +155,16 @@ Optional<NetworkSessionCreationParameters> NetworkSessionCreationParameters::dec
         return WTF::nullopt;
 #endif
 
+    Optional<String> hstsStorageDirectory;
+    decoder >> hstsStorageDirectory;
+    if (!hstsStorageDirectory)
+        return WTF::nullopt;
+
+    Optional<SandboxExtension::Handle> hstsStorageDirectoryExtensionHandle;
+    decoder >> hstsStorageDirectoryExtensionHandle;
+    if (!hstsStorageDirectoryExtensionHandle)
+        return WTF::nullopt;
+    
 #if USE(SOUP)
     Optional<String> cookiePersistentStoragePath;
     decoder >> cookiePersistentStoragePath;
@@ -275,6 +287,8 @@ Optional<NetworkSessionCreationParameters> NetworkSessionCreationParameters::dec
         , WTFMove(*alternativeServiceDirectoryExtensionHandle)
         , WTFMove(*http3Enabled)
 #endif
+        , WTFMove(*hstsStorageDirectory)
+        , WTFMove(*hstsStorageDirectoryExtensionHandle)
 #if USE(SOUP)
         , WTFMove(*cookiePersistentStoragePath)
         , WTFMove(*cookiePersistentStorageType)
index f677455..c342933 100644 (file)
@@ -69,6 +69,8 @@ struct NetworkSessionCreationParameters {
     SandboxExtension::Handle alternativeServiceDirectoryExtensionHandle;
     bool http3Enabled { false };
 #endif
+    String hstsStorageDirectory;
+    SandboxExtension::Handle hstsStorageDirectoryExtensionHandle;
 #if USE(SOUP)
     String cookiePersistentStoragePath;
     SoupCookiePersistentStorageType cookiePersistentStorageType { SoupCookiePersistentStorageType::Text };
index afbd930..d940b75 100644 (file)
@@ -134,6 +134,7 @@ RetainPtr<CFDataRef> NetworkProcess::sourceApplicationAuditData() const
 #endif
 }
 
+#if !HAVE(HSTS_STORAGE)
 static void filterPreloadHSTSEntry(const void* key, const void* value, void* context)
 {
     RELEASE_ASSERT(context);
@@ -152,27 +153,53 @@ static void filterPreloadHSTSEntry(const void* key, const void* value, void* con
     if (CFDictionaryGetValue(val, _kCFNetworkHSTSPreloaded) != kCFBooleanTrue)
         hostnames->add((CFStringRef)key);
 }
+#endif
 
-void NetworkProcess::getHostNamesWithHSTSCache(WebCore::NetworkStorageSession& session, HashSet<String>& hostNames)
+HashSet<String> NetworkProcess::hostNamesWithHSTSCache(PAL::SessionID sessionID) const
 {
-    if (auto HSTSPolicies = adoptCF(_CFNetworkCopyHSTSPolicies(session.platformSession())))
-        CFDictionaryApplyFunction(HSTSPolicies.get(), filterPreloadHSTSEntry, &hostNames);
+    HashSet<String> hostNames;
+#if HAVE(HSTS_STORAGE)
+    if (auto* networkSession = static_cast<NetworkSessionCocoa*>(this->networkSession(sessionID))) {
+        for (NSString *host in networkSession->hstsStorage().nonPreloadedHosts)
+            hostNames.add(host);
+    }
+#else
+    if (auto* session = storageSession(sessionID)) {
+        if (auto HSTSPolicies = adoptCF(_CFNetworkCopyHSTSPolicies(session->platformSession())))
+            CFDictionaryApplyFunction(HSTSPolicies.get(), filterPreloadHSTSEntry, &hostNames);
+    }
+#endif
+    return hostNames;
 }
 
-void NetworkProcess::deleteHSTSCacheForHostNames(WebCore::NetworkStorageSession& session, const Vector<String>& hostNames)
+void NetworkProcess::deleteHSTSCacheForHostNames(PAL::SessionID sessionID, const Vector<String>& hostNames)
 {
-    for (auto& hostName : hostNames) {
-        auto url = URL({ }, makeString("https://", hostName));
-        _CFNetworkResetHSTS(url.createCFURL().get(), session.platformSession());
+#if HAVE(HSTS_STORAGE)
+    if (auto* networkSession = static_cast<NetworkSessionCocoa*>(this->networkSession(sessionID))) {
+        for (auto& hostName : hostNames)
+            [networkSession->hstsStorage() resetHSTSForHost:hostName];
     }
+#else
+    if (auto* session = storageSession(sessionID)) {
+        for (auto& hostName : hostNames) {
+            auto url = URL({ }, makeString("https://", hostName));
+            _CFNetworkResetHSTS(url.createCFURL().get(), session->platformSession());
+        }
+    }
+#endif
 }
 
-void NetworkProcess::clearHSTSCache(WebCore::NetworkStorageSession& session, WallTime modifiedSince)
+void NetworkProcess::clearHSTSCache(PAL::SessionID sessionID, WallTime modifiedSince)
 {
     NSTimeInterval timeInterval = modifiedSince.secondsSinceEpoch().seconds();
     NSDate *date = [NSDate dateWithTimeIntervalSince1970:timeInterval];
-
-    _CFNetworkResetHSTSHostsSinceDate(session.platformSession(), (__bridge CFDateRef)date);
+#if HAVE(HSTS_STORAGE)
+    if (auto* networkSession = static_cast<NetworkSessionCocoa*>(this->networkSession(sessionID)))
+        [networkSession->hstsStorage() resetHSTSHostsSinceDate:date];
+#else
+    if (auto* session = storageSession(sessionID))
+        _CFNetworkResetHSTSHostsSinceDate(session->platformSession(), (__bridge CFDateRef)date);
+#endif
 }
 
 void NetworkProcess::clearDiskCache(WallTime modifiedSince, CompletionHandler<void()>&& completionHandler)
index 9ca8fa6..aa03921 100644 (file)
@@ -33,6 +33,7 @@ OBJC_CLASS NSURLSessionDownloadTask;
 OBJC_CLASS NSOperationQueue;
 OBJC_CLASS WKNetworkSessionDelegate;
 OBJC_CLASS WKNetworkSessionWebSocketDelegate;
+OBJC_CLASS _NSHSTSStorage;
 
 #include "DownloadID.h"
 #include "NetworkDataTaskCocoa.h"
@@ -104,6 +105,7 @@ public:
     void taskServerConnectionSucceeded(NetworkDataTaskCocoa::TaskIdentifier);
     void taskFailed(NetworkDataTaskCocoa::TaskIdentifier);
     NSURLCredential *successfulClientCertificateForHost(const String& host, uint16_t port) const;
+    _NSHSTSStorage *hstsStorage() const;
 
 private:
     void invalidateAndCancel() override;
index 78fd2d2..75a045a 100644 (file)
 
 #import "DeviceManagementSoftLink.h"
 
+// FIXME: Remove this soft link once rdar://problem/50109631 is in a build and bots are updated.
+SOFT_LINK_FRAMEWORK(CFNetwork)
+SOFT_LINK_CLASS_OPTIONAL(CFNetwork, _NSHSTSStorage)
+
 using namespace WebKit;
 
 CFStringRef const WebKit2HTTPProxyDefaultsKey = static_cast<CFStringRef>(@"WebKit2HTTPProxy");
@@ -1092,6 +1096,17 @@ NSURLCredential *NetworkSessionCocoa::successfulClientCertificateForHost(const S
     return m_successfulClientCertificates.get(key).get();
 }
 
+_NSHSTSStorage *NetworkSessionCocoa::hstsStorage() const
+{
+#if HAVE(HSTS_STORAGE)
+    NSURLSessionConfiguration *configuration = m_sessionWithCredentialStorage.session.get().configuration;
+    // FIXME: Remove this respondsToSelector check once rdar://problem/50109631 is in a build and bots are updated.
+    if ([configuration respondsToSelector:@selector(_hstsStorage)])
+        return m_sessionWithCredentialStorage.session.get().configuration._hstsStorage;
+#endif
+    return nil;
+}
+
 const String& NetworkSessionCocoa::boundInterfaceIdentifier() const
 {
     return m_boundInterfaceIdentifier;
@@ -1172,6 +1187,15 @@ NetworkSessionCocoa::NetworkSessionCocoa(NetworkProcess& networkProcess, Network
 
     NSURLSessionConfiguration *configuration = configurationForSessionID(m_sessionID);
 
+#if HAVE(HSTS_STORAGE)
+    if (!!parameters.hstsStorageDirectory && !m_sessionID.isEphemeral()) {
+        SandboxExtension::consumePermanently(parameters.hstsStorageDirectoryExtensionHandle);
+        // FIXME: Remove this respondsToSelector check once rdar://problem/50109631 is in a build and bots are updated.
+        if ([configuration respondsToSelector:@selector(_hstsStorage)])
+            configuration._hstsStorage = [[alloc_NSHSTSStorageInstance() initPersistentStoreWithURL:[NSURL fileURLWithPath:parameters.hstsStorageDirectory isDirectory:YES]] autorelease];
+    }
+#endif
+
 #if HAVE(APP_SSO) || PLATFORM(MACCATALYST)
     configuration._preventsAppSSO = true;
 #endif
index 60fa556..baf9bb9 100644 (file)
@@ -94,21 +94,23 @@ static CString buildAcceptLanguages(const Vector<String>& languages)
     return builder.toString().utf8();
 }
 
-void NetworkProcess::getHostNamesWithHSTSCache(WebCore::NetworkStorageSession& storageSession, HashSet<String>& hostNames)
+HashSet<String> NetworkProcess::hostNamesWithHSTSCache(PAL::SessionID sessionID) const
 {
-    const auto* session = static_cast<NetworkSessionSoup*>(networkSession(storageSession.sessionID()));
+    HashSet<String> hostNames;
+    const auto* session = static_cast<NetworkSessionSoup*>(networkSession(sessionID));
     session->soupNetworkSession().getHostNamesWithHSTSCache(hostNames);
+    return hostNames;
 }
 
-void NetworkProcess::deleteHSTSCacheForHostNames(WebCore::NetworkStorageSession& storageSession, const Vector<String>& hostNames)
+void NetworkProcess::deleteHSTSCacheForHostNames(PAL::SessionID sessionID, const Vector<String>& hostNames)
 {
-    const auto* session = static_cast<NetworkSessionSoup*>(networkSession(storageSession.sessionID()));
+    const auto* session = static_cast<NetworkSessionSoup*>(networkSession(sessionID));
     session->soupNetworkSession().deleteHSTSCacheForHostNames(hostNames);
 }
 
-void NetworkProcess::clearHSTSCache(WebCore::NetworkStorageSession& storageSession, WallTime modifiedSince)
+void NetworkProcess::clearHSTSCache(PAL::SessionID sessionID, WallTime modifiedSince)
 {
-    const auto* session = static_cast<NetworkSessionSoup*>(networkSession(storageSession.sessionID()));
+    const auto* session = static_cast<NetworkSessionSoup*>(networkSession(sessionID));
     session->soupNetworkSession().clearHSTSCache(modifiedSince);
 }
 
index 4686e3b..e98f5fd 100644 (file)
@@ -27,6 +27,7 @@
 #define WKContextPrivateMac_h
 
 #include <WebKit/WKBase.h>
+#include <WebKit/WKDeprecated.h>
 #include <WebKit/WKPluginLoadPolicy.h>
 
 #ifdef __cplusplus
@@ -43,10 +44,8 @@ WK_EXPORT WKDictionaryRef WKContextCopyPlugInInfoForBundleIdentifier(WKContextRe
 typedef void (^WKContextGetInfoForInstalledPlugInsBlock)(WKArrayRef, WKErrorRef);
 WK_EXPORT void WKContextGetInfoForInstalledPlugIns(WKContextRef context, WKContextGetInfoForInstalledPlugInsBlock block);
 
-WK_EXPORT void WKContextResetHSTSHosts(WKContextRef context);
-
-// The time here is relative to the Unix epoch.
-WK_EXPORT void WKContextResetHSTSHostsAddedAfterDate(WKContextRef context, double startDateIntervalSince1970);
+WK_EXPORT void WKContextResetHSTSHosts(WKContextRef context) WK_C_API_DEPRECATED;
+WK_EXPORT void WKContextResetHSTSHostsAddedAfterDate(WKContextRef context, double startDateIntervalSince1970) WK_C_API_DEPRECATED;
 
 WK_EXPORT void WKContextRegisterSchemeForCustomProtocol(WKContextRef context, WKStringRef scheme);
 WK_EXPORT void WKContextUnregisterSchemeForCustomProtocol(WKContextRef context, WKStringRef scheme);
index 13c0c6f..d3a0717 100644 (file)
@@ -101,14 +101,12 @@ void WKContextGetInfoForInstalledPlugIns(WKContextRef contextRef, WKContextGetIn
 #endif
 }
 
-void WKContextResetHSTSHosts(WKContextRef context)
+void WKContextResetHSTSHosts(WKContextRef)
 {
-    return WebKit::toImpl(context)->resetHSTSHosts();
 }
 
-void WKContextResetHSTSHostsAddedAfterDate(WKContextRef context, double startDateIntervalSince1970)
+void WKContextResetHSTSHostsAddedAfterDate(WKContextRef, double)
 {
-    return WebKit::toImpl(context)->resetHSTSHostsAddedAfterDate(startDateIntervalSince1970);
 }
 
 void WKContextRegisterSchemeForCustomProtocol(WKContextRef context, WKStringRef scheme)
index df2b919..7226cc2 100644 (file)
@@ -68,7 +68,7 @@ WK_CLASS_AVAILABLE(macos(10.10), ios(8.0))
 @property (nonatomic) BOOL usesWebProcessCache WK_API_AVAILABLE(macos(10.14.4), ios(12.2));
 @property (nonatomic) BOOL pageCacheEnabled WK_API_AVAILABLE(macos(10.14), ios(12.0));
 @property (nonatomic, getter=isJITEnabled) BOOL JITEnabled WK_API_AVAILABLE(macos(10.14.4), ios(12.2));
-@property (nonatomic, nullable, copy, setter=setHSTSStorageDirectory:) NSURL *hstsStorageDirectory WK_API_AVAILABLE(macos(10.15), ios(13.0));
+@property (nonatomic, nullable, copy, setter=setHSTSStorageDirectory:) NSURL *hstsStorageDirectory WK_API_DEPRECATED_WITH_REPLACEMENT("_WKWebsiteDataStoreConfiguration.hstsStorageDirectory", macos(10.15, WK_MAC_TBA), ios(13.0, WK_IOS_TBA));
 
 @property (nonatomic) BOOL configureJSCForTesting WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
 
index 29d8c59..71c13d8 100644 (file)
@@ -72,6 +72,7 @@ WK_CLASS_AVAILABLE(macos(10.13), ios(11.0))
 @property (nonatomic) NSUInteger testSpeedMultiplier WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
 @property (nonatomic) BOOL suppressesConnectionTerminationOnSystemChange WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
 @property (nonatomic) BOOL allowsServerPreconnect WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
+@property (nonatomic, nullable, copy, setter=setHSTSStorageDirectory:) NSURL *hstsStorageDirectory WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
 
 @property (nonatomic, nullable, copy) NSURL *alternativeServicesStorageDirectory WK_API_AVAILABLE(macos(WK_MAC_TBA), ios(WK_IOS_TBA));
 
index 0153116..bb97273 100644 (file)
@@ -290,6 +290,19 @@ static void checkURLArgument(NSURL *url)
     _configuration->setMediaKeysStorageDirectory(url.path);
 }
 
+- (NSURL *)hstsStorageDirectory
+{
+    return [NSURL fileURLWithPath:_configuration->hstsStorageDirectory() isDirectory:YES];
+}
+
+- (void)setHSTSStorageDirectory:(NSURL *)url
+{
+    if (!_configuration->isPersistent())
+        [NSException raise:NSInvalidArgumentException format:@"Cannot set mediaKeysStorageDirectory on a non-persistent _WKWebsiteDataStoreConfiguration."];
+    checkURLArgument(url);
+    _configuration->setHSTSStorageDirectory(url.path);
+}
+
 - (NSURL *)alternativeServicesStorageDirectory
 {
     return [NSURL fileURLWithPath:_configuration->alternativeServicesDirectory() isDirectory:YES];
index 1fa6031..a1760f8 100644 (file)
@@ -728,18 +728,6 @@ void WebProcessPool::unregisterNotificationObservers()
     [[NSNotificationCenter defaultCenter] removeObserver:m_activationObserver.get()];
 }
 
-static CFURLStorageSessionRef privateBrowsingSession()
-{
-    static CFURLStorageSessionRef session;
-    static dispatch_once_t once;
-    dispatch_once(&once, ^{
-        NSString *identifier = [NSString stringWithFormat:@"%@.PrivateBrowsing", [[NSBundle mainBundle] bundleIdentifier]];
-        session = createPrivateStorageSession((__bridge CFStringRef)identifier);
-    });
-
-    return session;
-}
-
 bool WebProcessPool::isURLKnownHSTSHost(const String& urlString) const
 {
     RetainPtr<CFURLRef> url = URL(URL(), urlString).createCFURL();
@@ -747,19 +735,6 @@ bool WebProcessPool::isURLKnownHSTSHost(const String& urlString) const
     return _CFNetworkIsKnownHSTSHostWithSession(url.get(), nullptr);
 }
 
-void WebProcessPool::resetHSTSHosts()
-{
-    _CFNetworkResetHSTSHostsWithSession(nullptr);
-    _CFNetworkResetHSTSHostsWithSession(privateBrowsingSession());
-}
-
-void WebProcessPool::resetHSTSHostsAddedAfterDate(double startDateIntervalSince1970)
-{
-    NSDate *startDate = [NSDate dateWithTimeIntervalSince1970:startDateIntervalSince1970];
-    _CFNetworkResetHSTSHostsSinceDate(nullptr, (__bridge CFDateRef)startDate);
-    _CFNetworkResetHSTSHostsSinceDate(privateBrowsingSession(), (__bridge CFDateRef)startDate);
-}
-
 #if PLATFORM(MAC) && ENABLE(WEBPROCESS_WINDOWSERVER_BLOCKING)
 Optional<unsigned> WebProcessPool::nominalFramesPerSecondForDisplay(WebCore::PlatformDisplayID displayID)
 {
index bf2d8c7..40bd8c1 100644 (file)
@@ -422,8 +422,6 @@ public:
     static void didReceiveInvalidMessage(IPC::MessageName);
 
     bool isURLKnownHSTSHost(const String& urlString) const;
-    void resetHSTSHosts();
-    void resetHSTSHostsAddedAfterDate(double startDateIntervalSince1970);
 
     static void registerGlobalURLSchemeAsHavingCustomProtocolHandlers(const String&);
     static void unregisterGlobalURLSchemeAsHavingCustomProtocolHandlers(const String&);
index ce9bd7f..d6ae1c8 100644 (file)
@@ -232,6 +232,8 @@ void WebsiteDataStore::resolveDirectoriesIfNecessary()
         m_resolvedConfiguration->setJavaScriptConfigurationDirectory(resolvePathForSandboxExtension(m_configuration->javaScriptConfigurationDirectory()));
     if (!m_configuration->cacheStorageDirectory().isEmpty() && m_resolvedConfiguration->cacheStorageDirectory().isEmpty())
         m_resolvedConfiguration->setCacheStorageDirectory(resolvePathForSandboxExtension(m_configuration->cacheStorageDirectory()));
+    if (!m_configuration->hstsStorageDirectory().isEmpty() && m_resolvedConfiguration->hstsStorageDirectory().isEmpty())
+        m_resolvedConfiguration->setHSTSStorageDirectory(resolvePathForSandboxExtension(m_configuration->hstsStorageDirectory()));
 
     // Resolve directories for file paths.
     if (!m_configuration->cookieStorageFile().isEmpty()) {
@@ -2259,6 +2261,11 @@ WebsiteDataStoreParameters WebsiteDataStore::parameters()
     if (!networkCacheDirectory.isEmpty())
         SandboxExtension::createHandleForReadWriteDirectory(networkCacheDirectory, networkCacheDirectoryExtensionHandle);
 
+    auto hstsStorageDirectory = resolvedHSTSStorageDirectory();
+    SandboxExtension::Handle hstsStorageDirectoryExtensionHandle;
+    if (!hstsStorageDirectory.isEmpty())
+        SandboxExtension::createHandleForReadWriteDirectory(hstsStorageDirectory, hstsStorageDirectoryExtensionHandle);
+
     bool shouldIncludeLocalhostInResourceLoadStatistics = false;
     bool enableResourceLoadStatisticsDebugMode = false;
     auto firstPartyWebsiteDataRemovalMode = WebCore::FirstPartyWebsiteDataRemovalMode::AllButCookies;
@@ -2300,6 +2307,8 @@ WebsiteDataStoreParameters WebsiteDataStore::parameters()
     networkSessionParameters.allLoadsBlockedByDeviceManagementRestrictionsForTesting = m_configuration->allLoadsBlockedByDeviceManagementRestrictionsForTesting();
     networkSessionParameters.networkCacheDirectory = WTFMove(networkCacheDirectory);
     networkSessionParameters.networkCacheDirectoryExtensionHandle = WTFMove(networkCacheDirectoryExtensionHandle);
+    networkSessionParameters.hstsStorageDirectory = WTFMove(hstsStorageDirectory);
+    networkSessionParameters.hstsStorageDirectoryExtensionHandle = WTFMove(hstsStorageDirectoryExtensionHandle);
     networkSessionParameters.dataConnectionServiceType = m_configuration->dataConnectionServiceType();
     networkSessionParameters.fastServerTrustEvaluationEnabled = m_configuration->fastServerTrustEvaluationEnabled();
     networkSessionParameters.networkCacheSpeculativeValidationEnabled = m_configuration->networkCacheSpeculativeValidationEnabled();
index e422adc..200558e 100644 (file)
@@ -224,6 +224,7 @@ public:
     const String& resolvedIndexedDatabaseDirectory() const { return m_resolvedConfiguration->indexedDBDatabaseDirectory(); }
     const String& resolvedServiceWorkerRegistrationDirectory() const { return m_resolvedConfiguration->serviceWorkerRegistrationDirectory(); }
     const String& resolvedResourceLoadStatisticsDirectory() const { return m_resolvedConfiguration->resourceLoadStatisticsDirectory(); }
+    const String& resolvedHSTSStorageDirectory() const { return m_resolvedConfiguration->hstsStorageDirectory(); }
 
     DeviceIdHashSaltStorage& deviceIdHashSaltStorage() { return m_deviceIdHashSaltStorage.get(); }
 
index a75a790..1b1bfa9 100644 (file)
@@ -67,9 +67,7 @@ Ref<WebsiteDataStoreConfiguration> WebsiteDataStoreConfiguration::copy() const
     copy->m_indexedDBDatabaseDirectory = this->m_indexedDBDatabaseDirectory;
     copy->m_serviceWorkerRegistrationDirectory = this->m_serviceWorkerRegistrationDirectory;
     copy->m_webSQLDatabaseDirectory = this->m_webSQLDatabaseDirectory;
-#if USE(GLIB)
     copy->m_hstsStorageDirectory = this->m_hstsStorageDirectory;
-#endif
     copy->m_localStorageDirectory = this->m_localStorageDirectory;
     copy->m_mediaKeysStorageDirectory = this->m_mediaKeysStorageDirectory;
     copy->m_alternativeServicesDirectory = this->m_alternativeServicesDirectory;
index 5dc7221..cbb7edc 100644 (file)
@@ -66,10 +66,10 @@ public:
 
     const String& webSQLDatabaseDirectory() const { return m_webSQLDatabaseDirectory; }
     void setWebSQLDatabaseDirectory(String&& directory) { m_webSQLDatabaseDirectory = WTFMove(directory); }
-#if USE(GLIB) // According to r245075 this will eventually move here.
+
     const String& hstsStorageDirectory() const { return m_hstsStorageDirectory; }
     void setHSTSStorageDirectory(String&& directory) { m_hstsStorageDirectory = WTFMove(directory); }
-#endif
+
     const String& localStorageDirectory() const { return m_localStorageDirectory; }
     void setLocalStorageDirectory(String&& directory) { m_localStorageDirectory = WTFMove(directory); }
 
@@ -174,8 +174,8 @@ private:
     String m_indexedDBDatabaseDirectory;
     String m_serviceWorkerRegistrationDirectory;
     String m_webSQLDatabaseDirectory;
-#if USE(GLIB)
     String m_hstsStorageDirectory;
+#if USE(GLIB)
     bool m_networkCacheSpeculativeValidationEnabled { true };
 #else
     bool m_networkCacheSpeculativeValidationEnabled { false };