⚠ Archived content — this site is no longer maintained.   Current WebKit documentation is at docs.webkit.org.

Changeset 248734 in webkit


Ignore:
Timestamp:
Aug 15, 2019, 11:41:53 AM (7 years ago)
Author:
sihui_liu@apple.com
Message:

Some improvements on web storage
​https://bugs.webkit.org/show_bug.cgi?id=200373

Reviewed by Geoffrey Garen.
Source/WebCore:

Remove storage type EphemeralLocalStorage, which is used for localStorage in ephemeral session, and use
LocalStorage instead.

Add SessionID to StorageNamespace to make StorageNamespace session-specific.

No new test, updating existing tests for new behavior.

  • loader/EmptyClients.cpp:

(WebCore::EmptyStorageNamespaceProvider::createLocalStorageNamespace):
(WebCore::EmptyStorageNamespaceProvider::createTransientLocalStorageNamespace):
(WebCore::EmptyStorageNamespaceProvider::createEphemeralLocalStorageNamespace): Deleted.

  • page/Chrome.cpp:

(WebCore::Chrome::createWindow const): ephemeral localStorage of different windows will connect to the same
StorageArea in network process, so no need to copy from parent window to child window.

  • page/DOMWindow.cpp:

(WebCore::DOMWindow::prewarmLocalStorageIfNecessary): localStorage will be prewarmed in network process in the
initialization of StorageAreaMap.

  • page/Page.cpp:

(WebCore::m_applicationManifest):
(WebCore::Page::~Page):
(WebCore::Page::setSessionID):
(WebCore::Page::ephemeralLocalStorage): Deleted.
(WebCore::Page::setEphemeralLocalStorage): Deleted.
(WebCore::Page::setStorageNamespaceProvider): Deleted.

  • page/Page.h:

(WebCore::Page::storageNamespaceProvider):

  • storage/Storage.cpp:

(WebCore::Storage::prewarm): Deleted.

  • storage/Storage.h:
  • storage/StorageArea.h:

(WebCore::StorageArea::closeDatabaseIfIdle):
(WebCore::StorageArea::prewarm): Deleted.

  • storage/StorageNamespace.h:
  • storage/StorageNamespaceProvider.cpp:

(WebCore::StorageNamespaceProvider::~StorageNamespaceProvider):
(WebCore::StorageNamespaceProvider::localStorageArea):
(WebCore::StorageNamespaceProvider::localStorageNamespace):
(WebCore::StorageNamespaceProvider::transientLocalStorageNamespace):
(WebCore::StorageNamespaceProvider::enableLegacyPrivateBrowsingForTesting): change SessionID of storageNamespace
and update every StorageArea in this namespace.
(WebCore::StorageNamespaceProvider::addPage): Deleted.
(WebCore::StorageNamespaceProvider::removePage): Deleted.

  • storage/StorageNamespaceProvider.h:
  • storage/StorageType.h:

(WebCore::isLocalStorage):

Source/WebKit:

Fix some issues in web storage architecture. For example, sessionStorageNameSpace for web page is prepared and
destroyed in the network process when the page comes and goes, even though the page may not use sessionStorage
at all. The messages about page state sent from web process to network process can be waste.

Here are some general ideas of this patch:

  1. Network process owns the web storage, and web process keeps a small local copy (based on session and

origins that are visited). There is a virtual connection from the local copy in the web process to the original
copy in the network process. The connection is created by web process when some page asks for web storage.

  1. If connection is lost because network process is gone, storage in memory will be lost. The local copy in web

processs will be discarded.

  1. (SessionID, StorageNamespaceID, SecurityOrigin) is used to identify a storage area. If session is changed in

web process (like enabling private browsing in layout test now), a re-connection with different sessionID would
suffice to load another copy of storage.

  1. localStorage in ephemeral session has the same behavior as localStorage instead of sessionStorage, which

means different pages in the same ephemeral session share the same localStorage.

Also, this patch introduces StorageManagerSet to network process. It handles web storage stuff, including
receiving storage messages from web process, on one background thread. Previously each session has its own
StorageManager and each StorageManager has its own WorkQueue.

  • CMakeLists.txt:
  • DerivedSources-input.xcfilelist:
  • DerivedSources-output.xcfilelist:
  • DerivedSources.make:
  • NetworkProcess/NetworkConnectionToWebProcess.cpp: remove message handlers that are no longer needed. Network

process no longer needs to know page states from web process.
(WebKit::NetworkConnectionToWebProcess::didClose):
(WebKit::NetworkConnectionToWebProcess::webPageWasAdded): Deleted.
(WebKit::NetworkConnectionToWebProcess::webPageWasRemoved): Deleted.
(WebKit::NetworkConnectionToWebProcess::webProcessSessionChanged): Deleted.

  • NetworkProcess/NetworkConnectionToWebProcess.h:
  • NetworkProcess/NetworkConnectionToWebProcess.messages.in:
  • NetworkProcess/NetworkProcess.cpp: NetworkProcess uses StorageManagerSet instead of StorageManager from

different sessions to deal with web storage.
(WebKit::NetworkProcess::NetworkProcess):
(WebKit::NetworkProcess::initializeNetworkProcess):
(WebKit::NetworkProcess::createNetworkConnectionToWebProcess): StorageManagerSet starts handling
StorageManagerSet messages from the new connection.
(WebKit::NetworkProcess::addWebsiteDataStore):
(WebKit::NetworkProcess::destroySession):
(WebKit::NetworkProcess::hasLocalStorage):
(WebKit::NetworkProcess::fetchWebsiteData):
(WebKit::NetworkProcess::deleteWebsiteData):
(WebKit::NetworkProcess::deleteWebsiteDataForOrigins):
(WebKit::NetworkProcess::deleteWebsiteDataForRegistrableDomains):
(WebKit::NetworkProcess::actualPrepareToSuspend):
(WebKit::NetworkProcess::resume):
(WebKit::NetworkProcess::syncLocalStorage):
(WebKit::NetworkProcess::clearLegacyPrivateBrowsingLocalStorage): added for clearing in-memory ephemeral
localStorage.
(WebKit::NetworkProcess::getLocalStorageOriginDetails):
(WebKit::NetworkProcess::connectionToWebProcessClosed):
(WebKit::NetworkProcess::webPageWasAdded): Deleted.
(WebKit::NetworkProcess::webPageWasRemoved): Deleted.
(WebKit::NetworkProcess::webProcessWasDisconnected): Deleted.
(WebKit::NetworkProcess::webProcessSessionChanged): Deleted.

  • NetworkProcess/NetworkProcess.h:
  • NetworkProcess/NetworkProcess.messages.in:
  • NetworkProcess/NetworkSession.cpp: StorageManager is moved out of NetworkSession. It is now managed by

StorageManagerSet.
(WebKit::NetworkSession::NetworkSession):
(WebKit::NetworkSession::~NetworkSession):

  • NetworkProcess/NetworkSession.h:

(WebKit::NetworkSession::storageManager): Deleted.

  • NetworkProcess/NetworkSessionCreationParameters.cpp: creation parameters of StorageManager is moved out of

NetworkSessionCreationParameters.
(WebKit::NetworkSessionCreationParameters::privateSessionParameters):
(WebKit::NetworkSessionCreationParameters::encode const):
(WebKit::NetworkSessionCreationParameters::decode):

  • NetworkProcess/NetworkSessionCreationParameters.h:
  • NetworkProcess/WebStorage/LocalStorageDatabase.cpp:

(WebKit::LocalStorageDatabase::updateDatabase): remove an assertion that is no longer true as we can force an
update with syncLocalStorage now.

  • NetworkProcess/WebStorage/LocalStorageDatabase.h: make updateDatabase public for syncLocalStorage.
  • NetworkProcess/WebStorage/LocalStorageDatabaseTracker.cpp: LocalStorageDatabaseTracker is created on the

background thread now, so it does not hold WorkQueue to do the file operation.
(WebKit::LocalStorageDatabaseTracker::create):
(WebKit::LocalStorageDatabaseTracker::LocalStorageDatabaseTracker):
(WebKit::LocalStorageDatabaseTracker::~LocalStorageDatabaseTracker):

  • NetworkProcess/WebStorage/LocalStorageDatabaseTracker.h:
  • NetworkProcess/WebStorage/LocalStorageNamespace.cpp:

(WebKit::LocalStorageNamespace::getOrCreateStorageArea):
(WebKit::LocalStorageNamespace::cloneTo): Deleted.

  • NetworkProcess/WebStorage/LocalStorageNamespace.h:
  • NetworkProcess/WebStorage/SessionStorageNamespace.cpp:

(WebKit::SessionStorageNamespace::getOrCreateStorageArea):
(WebKit::SessionStorageNamespace::addAllowedConnection): Deleted.
(WebKit::SessionStorageNamespace::removeAllowedConnection): Deleted.

  • NetworkProcess/WebStorage/SessionStorageNamespace.h:

(WebKit::SessionStorageNamespace::allowedConnections const): Deleted.

  • NetworkProcess/WebStorage/StorageArea.cpp:

(WebKit::generateStorageAreaIdentifier): each StorageArea has an identifier. StorageAreaMap in web process uses
this identifier to indicate which StorageArea it is connecting to.
(WebKit::StorageArea::StorageArea):
(WebKit::StorageArea::~StorageArea): StorageArea may still have listeners because StorageArea should be
destroyed by requests from UI process, and listeners are connections to web processses.
(WebKit::StorageArea::addListener): load localStorageDatabase in advance if there is some connection to this
LocalStorage area.
(WebKit::StorageArea::removeListener):
(WebKit::StorageArea::hasListener const):
(WebKit::StorageArea::clear):
(WebKit::StorageArea::openDatabaseAndImportItemsIfNeeded const):
(WebKit::StorageArea::dispatchEvents const):
(WebKit::StorageArea::syncToDatabase):
(WebKit::StorageArea::setItems): Deleted. Stop syncing from web process to network process after network process
is relaunched.

  • NetworkProcess/WebStorage/StorageArea.h:

(WebKit::StorageArea::identifier):
(WebKit::StorageArea::setWorkQueue):

  • NetworkProcess/WebStorage/StorageManager.cpp: StorageManager should be accessed by only background thread now.

(WebKit::StorageManager::StorageManager):
(WebKit::StorageManager::~StorageManager):
(WebKit::StorageManager::createSessionStorageNamespace):
(WebKit::StorageManager::destroySessionStorageNamespace): this is not used now but keep it for future
improvement to remove in-memory sessionStorage in network process if we know some web page is gone forever.
(WebKit::StorageManager::cloneSessionStorageNamespace): previously each page had its own ephemeral
localStorageNamespace and now all pages in the same session share one localStorage, so we don't need to clone
localStorageNamespace.
(WebKit::StorageManager::getSessionStorageOrigins):
(WebKit::StorageManager::deleteSessionStorageOrigins):
(WebKit::StorageManager::deleteSessionStorageEntriesForOrigins):
(WebKit::StorageManager::getLocalStorageOrigins):
(WebKit::StorageManager::getLocalStorageOriginDetails):
(WebKit::StorageManager::deleteLocalStorageOriginsModifiedSince):
(WebKit::StorageManager::deleteLocalStorageEntriesForOrigins):
(WebKit::StorageManager::createLocalStorageArea):
(WebKit::StorageManager::createTransientLocalStorageArea):
(WebKit::StorageManager::createSessionStorageArea):
(WebKit::StorageManager::getOrCreateLocalStorageNamespace):
(WebKit::StorageManager::getOrCreateTransientLocalStorageNamespace):
(WebKit::StorageManager::getOrCreateSessionStorageNamespace):
(WebKit::StorageManager::clearStorageNamespaces):
(WebKit::StorageManager::addAllowedSessionStorageNamespaceConnection): Deleted.
(WebKit::StorageManager::removeAllowedSessionStorageNamespaceConnection): Deleted.
(WebKit::StorageManager::processDidCloseConnection): Deleted.
(WebKit::StorageManager::deleteLocalStorageEntriesForOrigin): Deleted.
(WebKit::StorageManager::createLocalStorageMap): Deleted.
(WebKit::StorageManager::createTransientLocalStorageMap): Deleted.
(WebKit::StorageManager::createSessionStorageMap): Deleted.
(WebKit::StorageManager::destroyStorageMap): Deleted.
(WebKit::StorageManager::prewarm): Deleted.
(WebKit::StorageManager::getValues): Deleted.
(WebKit::StorageManager::setItem): Deleted.
(WebKit::StorageManager::setItems): Deleted.
(WebKit::StorageManager::removeItem): Deleted.
(WebKit::StorageManager::clear): Deleted.
(WebKit::StorageManager::waitUntilTasksFinished): Deleted.
(WebKit::StorageManager::suspend): Deleted.
(WebKit::StorageManager::resume): Deleted.
(WebKit::StorageManager::findStorageArea const): Deleted.

  • NetworkProcess/WebStorage/StorageManager.h:

(WebKit::StorageManager::workQueue const): Deleted.
(): Deleted.

  • NetworkProcess/WebStorage/StorageManager.messages.in: Removed. Moved to StorageManagerSet.messages.in.
  • NetworkProcess/WebStorage/StorageManagerSet.cpp: Added.

(WebKit::StorageManagerSet::create):
(WebKit::StorageManagerSet::StorageManagerSet):
(WebKit::StorageManagerSet::~StorageManagerSet):
(WebKit::StorageManagerSet::add):
(WebKit::StorageManagerSet::remove):
(WebKit::StorageManagerSet::contains):
(WebKit::StorageManagerSet::addConnection):
(WebKit::StorageManagerSet::removeConnection):
(WebKit::StorageManagerSet::waitUntilTasksFinished):
(WebKit::StorageManagerSet::waitUntilSyncingLocalStorageFinished):
(WebKit::StorageManagerSet::suspend):
(WebKit::StorageManagerSet::resume):
(WebKit::StorageManagerSet::getSessionStorageOrigins):
(WebKit::StorageManagerSet::deleteSessionStorage):
(WebKit::StorageManagerSet::deleteSessionStorageForOrigins):
(WebKit::StorageManagerSet::getLocalStorageOrigins):
(WebKit::StorageManagerSet::deleteLocalStorageModifiedSince):
(WebKit::StorageManagerSet::deleteLocalStorageForOrigins):
(WebKit::StorageManagerSet::getLocalStorageOriginDetails):
(WebKit::StorageManagerSet::connectToLocalStorageArea):
(WebKit::StorageManagerSet::connectToTransientLocalStorageArea):
(WebKit::StorageManagerSet::connectToSessionStorageArea):
(WebKit::StorageManagerSet::disconnectFromStorageArea):
(WebKit::StorageManagerSet::getValues):
(WebKit::StorageManagerSet::setItem):
(WebKit::StorageManagerSet::removeItem):
(WebKit::StorageManagerSet::clear):
(WebKit::StorageManagerSet::cloneSessionStorageNamespace):

  • NetworkProcess/WebStorage/StorageManagerSet.h: Added.
  • NetworkProcess/WebStorage/StorageManagerSet.messages.in: Added.
  • Shared/WebsiteDataStoreParameters.cpp: creation parameters of StorageManager are moved to

WebsiteDataStoreParameters.
(WebKit::WebsiteDataStoreParameters::encode const):
(WebKit::WebsiteDataStoreParameters::decode):
(WebKit::WebsiteDataStoreParameters::privateSessionParameters):

  • Shared/WebsiteDataStoreParameters.h:
  • Sources.txt:
  • UIProcess/API/C/WKContext.cpp: add SPI for tests.

(WKContextSyncLocalStorage):
(WKContextClearLegacyPrivateBrowsingLocalStorage):

  • UIProcess/API/C/WKContextPrivate.h:
  • UIProcess/API/C/WKWebsiteDataStoreRef.cpp:

(WKWebsiteDataStoreRemoveLocalStorage):

  • UIProcess/API/C/WKWebsiteDataStoreRef.h:
  • UIProcess/WebProcessPool.cpp:

(WebKit::WebProcessPool::ensureNetworkProcess):
(WebKit::WebProcessPool::syncLocalStorage):
(WebKit::WebProcessPool::clearLegacyPrivateBrowsingLocalStorage):

  • UIProcess/WebProcessPool.h:
  • UIProcess/WebsiteData/Cocoa/WebsiteDataStoreCocoa.mm:

(WebKit::WebsiteDataStore::parameters):

  • UIProcess/WebsiteData/WebsiteDataStore.cpp:

(WebKit::WebsiteDataStore::parameters):

  • WebKit.xcodeproj/project.pbxproj:
  • WebProcess/InjectedBundle/InjectedBundle.cpp: session change of web storage is done via

WebStorageNamespaceProvider instead of WebProcess now.
(WebKit::InjectedBundle::setPrivateBrowsingEnabled):

  • WebProcess/WebProcess.cpp: web process no longer sends messsages about page state to network process.

(WebKit::WebProcess::createWebPage):
(WebKit::WebProcess::removeWebPage):
(WebKit::WebProcess::ensureNetworkProcessConnection):
(WebKit::WebProcess::networkProcessConnectionClosed):
(WebKit::WebProcess::storageAreaMap const):
(WebKit::WebProcess::enablePrivateBrowsingForTesting): Deleted. This was used for changing session via
WebProcess.

  • WebProcess/WebProcess.h:
  • WebProcess/WebStorage/StorageAreaImpl.cpp:

(WebKit::StorageAreaImpl::StorageAreaImpl):
(WebKit::StorageAreaImpl::length):
(WebKit::StorageAreaImpl::key):
(WebKit::StorageAreaImpl::item):
(WebKit::StorageAreaImpl::setItem):
(WebKit::StorageAreaImpl::removeItem):
(WebKit::StorageAreaImpl::clear):
(WebKit::StorageAreaImpl::contains):
(WebKit::StorageAreaImpl::storageType const):
(WebKit::StorageAreaImpl::incrementAccessCount):
(WebKit::StorageAreaImpl::decrementAccessCount):
(WebKit::StorageAreaImpl::prewarm): Deleted.
(WebKit::StorageAreaImpl::securityOrigin const): Deleted.

  • WebProcess/WebStorage/StorageAreaImpl.h: make StorageAreaImpl hold a weak reference to StorageAreaMap and

StorageNamespaceImpl hold a strong reference. In this way lifeime of localStorage StorageAreraMap stays align
with StorageNameSpaceProvider and Page.

  • WebProcess/WebStorage/StorageAreaMap.cpp: identifier of StorageAreaMap is the same as identifier of

StorageArea it connects to. If the identifier is 0, it means the StorageAreaMap is disconnected.
(WebKit::StorageAreaMap::StorageAreaMap):
(WebKit::StorageAreaMap::~StorageAreaMap):
(WebKit::StorageAreaMap::setItem):
(WebKit::StorageAreaMap::removeItem):
(WebKit::StorageAreaMap::clear):
(WebKit::StorageAreaMap::resetValues):
(WebKit::StorageAreaMap::loadValuesIfNeeded):
(WebKit::StorageAreaMap::applyChange):
(WebKit::StorageAreaMap::dispatchStorageEvent):
(WebKit::StorageAreaMap::dispatchSessionStorageEvent):
(WebKit::StorageAreaMap::dispatchLocalStorageEvent):
(WebKit::StorageAreaMap::connect):
(WebKit::StorageAreaMap::disconnect):
(WebKit::generateStorageMapID): Deleted.
(WebKit::StorageAreaMap::prewarm): Deleted.
(WebKit::StorageAreaMap::didGetValues): Deleted. This is useless as GetValues is a synchronous operation.

  • WebProcess/WebStorage/StorageAreaMap.h:

(): Deleted.

  • WebProcess/WebStorage/StorageAreaMap.messages.in: there are two synchronous messages, one for connection and

one for getting values. We may merge them into one in future improvement.

  • WebProcess/WebStorage/StorageNamespaceImpl.cpp:

(WebKit::StorageNamespaceImpl::createSessionStorageNamespace):
(WebKit::StorageNamespaceImpl::createLocalStorageNamespace):
(WebKit::StorageNamespaceImpl::createTransientLocalStorageNamespace):
(WebKit::StorageNamespaceImpl::StorageNamespaceImpl):
(WebKit::StorageNamespaceImpl::storageArea):
(WebKit::StorageNamespaceImpl::copy):
(WebKit::StorageNamespaceImpl::setSessionIDForTesting):
(WebKit::StorageNamespaceImpl::createEphemeralLocalStorageNamespace): Deleted.

  • WebProcess/WebStorage/StorageNamespaceImpl.h:
  • WebProcess/WebStorage/WebStorageNamespaceProvider.cpp:

(WebKit::WebStorageNamespaceProvider::createSessionStorageNamespace):
(WebKit::WebStorageNamespaceProvider::createLocalStorageNamespace):
(WebKit::WebStorageNamespaceProvider::createTransientLocalStorageNamespace):
(WebKit::WebStorageNamespaceProvider::createEphemeralLocalStorageNamespace): Deleted.

  • WebProcess/WebStorage/WebStorageNamespaceProvider.h:

Source/WebKitLegacy:

Do some clean-up and add support for session change of web storage in layout tests.

  • Storage/StorageAreaImpl.cpp:

(WebKit::StorageAreaImpl::sessionChanged):

  • Storage/StorageAreaImpl.h:

(): Deleted.

  • Storage/StorageAreaSync.h: make sure StorageAreaSync is destructed on the main thread, as it can be

dereferenced in StorageAreaImpl::sessionChanged and its last reference for final sync could be released on the
background thread.

  • Storage/StorageNamespaceImpl.cpp: replace EphemeralLocalStorage with LocalStorage, and store SessionID in

StorageNamespace.
(WebKit::StorageNamespaceImpl::createSessionStorageNamespace):
(WebKit::StorageNamespaceImpl::getOrCreateLocalStorageNamespace):
(WebKit::StorageNamespaceImpl::StorageNamespaceImpl):
(WebKit::StorageNamespaceImpl::copy):
(WebKit::StorageNamespaceImpl::close):
(WebKit::StorageNamespaceImpl::setSessionIDForTesting):
(WebKit::StorageNamespaceImpl::createEphemeralLocalStorageNamespace): Deleted.

  • Storage/StorageNamespaceImpl.h:
  • Storage/WebStorageNamespaceProvider.cpp:

(WebKit::WebStorageNamespaceProvider::createSessionStorageNamespace):
(WebKit::WebStorageNamespaceProvider::createLocalStorageNamespace):
(WebKit::WebStorageNamespaceProvider::createTransientLocalStorageNamespace):
(WebKit::WebStorageNamespaceProvider::createEphemeralLocalStorageNamespace): Deleted.

  • Storage/WebStorageNamespaceProvider.h:

Source/WebKitLegacy/mac:

  • WebView/WebView.mm:

(-[WebView _preferencesChanged:]): notify storageNamespaceProvider about session change.

Tools:

  • TestWebKitAPI/Tests/WebKitCocoa/LocalStoragePersistence.mm:

(TEST): update expectation for behavior change.

  • WebKitTestRunner/InjectedBundle/Bindings/TestRunner.idl: new SPI to synchronously flush localStorage to

database file.

  • WebKitTestRunner/InjectedBundle/TestRunner.cpp:

(WTR::TestRunner::syncLocalStorage):

  • WebKitTestRunner/InjectedBundle/TestRunner.h:
  • WebKitTestRunner/TestController.cpp: clear local storage between test runs to make each test isolated.

(WTR::TestController::resetStateToConsistentValues):
(WTR::StorageVoidCallbackContext::StorageVoidCallbackContext):
(WTR::StorageVoidCallback):
(WTR::TestController::clearIndexedDatabases):
(WTR::TestController::clearLocalStorage):
(WTR::TestController::syncLocalStorage):
(WTR::RemoveAllIndexedDatabasesCallbackContext::RemoveAllIndexedDatabasesCallbackContext): Deleted. Replaced
with StorageVoidCallbackContext for general usage.
(WTR::RemoveAllIndexedDatabasesCallback): Deleted. Replaced with StorageVoidCallback.
(WTR::TestController::ClearIndexedDatabases): Deleted. Use lowercase for consistent style.

  • WebKitTestRunner/TestController.h:
  • WebKitTestRunner/TestInvocation.cpp:

(WTR::TestInvocation::didReceiveSynchronousMessageFromInjectedBundle): add handler for new message
SyncLocalStorage.

LayoutTests:

Modify tests for a behavior change: sessionStorage will be lost when network process crashes.

For tests which use sessionStorage to store items, crash network process, then read from sessionStorage and
expect items to be in sessionStorage, replace sessionStorage with localStorage. Also, to make sure localStorage
is stored persistently before network process gets terminated, adopt a newly introduced SPI to
synchronously flush localStorage content to disk before terminating network process.

  • platform/ios-simulator-wk2/TestExpectations:
  • platform/mac-wk2/TestExpectations:
  • storage/domstorage/localstorage/private-browsing-affects-storage-expected.txt:
  • storage/indexeddb/IDBObject-leak.html:
  • storage/indexeddb/modern/opendatabase-after-storage-crash-expected.txt:
  • storage/indexeddb/modern/opendatabase-after-storage-crash.html:
Location:
trunk
Files:
3 added
1 deleted
89 edited

Legend:

Unmodified
Added
Removed
  • trunk/LayoutTests/ChangeLog

    r248733 r248734  
     12019-08-15  Sihui Liu  <sihui_liu@apple.com>
     2
     3        Some improvements on web storage
     4        https://bugs.webkit.org/show_bug.cgi?id=200373
     5
     6        Reviewed by Geoffrey Garen.
     7 
     8        Modify tests for a behavior change: sessionStorage will be lost when network process crashes.
     9
     10        For tests which use sessionStorage to store items, crash network process, then read from sessionStorage and
     11        expect items to be in sessionStorage, replace sessionStorage with localStorage. Also, to make sure localStorage
     12        is stored persistently before network process gets terminated, adopt a newly introduced SPI to
     13        synchronously flush localStorage content to disk before terminating network process.
     14
     15        * platform/ios-simulator-wk2/TestExpectations:
     16        * platform/mac-wk2/TestExpectations:
     17        * storage/domstorage/localstorage/private-browsing-affects-storage-expected.txt:
     18        * storage/indexeddb/IDBObject-leak.html:
     19        * storage/indexeddb/modern/opendatabase-after-storage-crash-expected.txt:
     20        * storage/indexeddb/modern/opendatabase-after-storage-crash.html:
     21
    1222019-08-15  Wenson Hsieh  <wenson_hsieh@apple.com>
    223
  • trunk/LayoutTests/platform/ios-simulator-wk2/TestExpectations

    r246641 r248734  
    6767http/wpt/cache-storage/cache-quota-add.any.html [ Slow ]
    6868
    69 webkit.org/b/196376 [ Debug ] storage/domstorage/localstorage/private-browsing-affects-storage.html [ Pass Failure ]
     69webkit.org/b/196376 [ Debug ] storage/domstorage/localstorage/private-browsing-affects-storage.html [ Pass ]
    7070
    7171webkit.org/b/196403 imported/w3c/web-platform-tests/mediacapture-record/MediaRecorder-stop.html [ Pass Failure ]
  • trunk/LayoutTests/platform/mac-wk2/TestExpectations

    r248679 r248734  
    923923webkit.org/b/194916 fast/mediastream/MediaStream-video-element.html [ Pass Failure ]
    924924
    925 webkit.org/b/196376 storage/domstorage/localstorage/private-browsing-affects-storage.html [ Pass Failure ]
     925webkit.org/b/196376 storage/domstorage/localstorage/private-browsing-affects-storage.html [ Pass ]
    926926
    927927webkit.org/b/196400 fast/mediastream/MediaStreamTrack-getSettings.html [ Pass Failure ]
  • trunk/LayoutTests/storage/domstorage/localstorage/private-browsing-affects-storage-expected.txt

    r215315 r248734  
    99ALERT: The item in new window is now: NewWindowValue
    1010ALERT: Back in parent window, localStorage's length is: 1
    11 ALERT: Back in parent window, testItem is: ChangedValue
     11ALERT: Back in parent window, testItem is: NewWindowValue
    1212ALERT: Final window, localStorage's length is: 1
    1313ALERT: Final window, item is: Persistent item!
  • trunk/LayoutTests/storage/indexeddb/IDBObject-leak.html

    r242043 r248734  
    1414    }
    1515
    16     if (sessionStorage.doneFirstLoad) {
     16    if (localStorage.doneFirstLoad) {
    1717        gc();
    1818        shouldBeEqualToNumber("internals.numberOfIDBTransactions()", 0);
    … …  
    2424    var request =  window.indexedDB.open(dbname);
    2525    request.onupgradeneeded = function(evt) {
    26         sessionStorage.doneFirstLoad = true;
     26        localStorage.doneFirstLoad = true;
    2727        if (!window.testRunner || !testRunner.terminateNetworkProcess) {
    2828            testFailed('This test requires access to the TestRunner object and terminateNetworkProcess() function');
    … …  
    3030            return;
    3131        }
     32
     33        // Make sure localStorage is flushed to disk before crashing network process.
     34        testRunner.syncLocalStorage();
    3235        testRunner.terminateNetworkProcess();
    33         setTimeout((()=> {
    34             location.reload();
    35         }), 0);
     36        evt.target.result.onerror = function(e) {
     37            setTimeout((()=> {
     38                location.reload();
     39            }), 0);
     40        }
    3641    }
    3742}
  • trunk/LayoutTests/storage/indexeddb/modern/opendatabase-after-storage-crash-expected.txt

    r234077 r248734  
    1 PASS sessionStorage[storageKey] is "Made it"
     1PASS localStorage[storageKey] is "Made it"
    22Successfully opened database with version 3.
  • trunk/LayoutTests/storage/indexeddb/modern/opendatabase-after-storage-crash.html

    r236035 r248734  
    2121                // Good, we received an expected error.
    2222                // Now reload to see if a new document connects successfully
    23                 if (sessionStorage[storageKey]) {
     23                if (localStorage[storageKey]) {
    2424                        document.body.innerHTML = "Received error more than once unexpectedly. Database: name " + dbname + ", version 2.";
    2525                        if (window.testRunner)
    … …  
    2828                }
    2929
    30                 sessionStorage[storageKey] = "Made it";
     30                localStorage[storageKey] = "Made it";
    3131                location.reload();
    3232        }
    3333
    3434        request.onsuccess = function(e) {
    35                 document.body.innerHTML = "Unexpected upgradeneeded after storage process termination. Database: name " + dbname + ", version 2. SessionStorage value: " + sessionStorage[storageKey] + ".";
     35                document.body.innerHTML = "Unexpected upgradeneeded after storage process termination. Database: name " + dbname + ", version 2. localStorage value: " + sessionStorage[storageKey] + ".";
    3636                if (window.testRunner)
    3737                        testRunner.notifyDone();
    … …  
    3939}
    4040
    41 var versionToOpen = sessionStorage.doneFirstLoad ? 3 : 1;
     41var versionToOpen = localStorage.doneFirstLoad ? 3 : 1;
    4242var request = window.indexedDB.open(dbname, versionToOpen);
    4343
    4444request.onupgradeneeded = function(e) {
    45         if (sessionStorage.doneFirstLoad) {
     45        if (localStorage.doneFirstLoad) {
    4646                document.body.innerHTML = "Successfully opened database with version " + versionToOpen + ".";
    47                 shouldBeEqualToString('sessionStorage[storageKey]', 'Made it');
     47                shouldBeEqualToString('localStorage[storageKey]', 'Made it');
    4848
    4949                if (window.testRunner) {
    … …  
    5353        }
    5454
    55         sessionStorage.doneFirstLoad = true;
     55        localStorage.doneFirstLoad = true;
    5656
    5757        // Set an error handler on the database connection so once the storage process terminates we know to continue the test
    … …  
    6262        if (window.testRunner) {
    6363                testRunner.waitUntilDone();
     64                // Make sure localStorage is flushed to disk before crashing network process.
     65                testRunner.syncLocalStorage();
    6466                testRunner.terminateNetworkProcess();
    6567        }
  • trunk/Source/WebCore/ChangeLog

    r248730 r248734  
     12019-08-15  Sihui Liu  <sihui_liu@apple.com>
     2
     3        Some improvements on web storage
     4        https://bugs.webkit.org/show_bug.cgi?id=200373
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        Remove storage type EphemeralLocalStorage, which is used for localStorage in ephemeral session, and use
     9        LocalStorage instead.
     10
     11        Add SessionID to StorageNamespace to make StorageNamespace session-specific.
     12
     13        No new test, updating existing tests for new behavior.
     14
     15        * loader/EmptyClients.cpp:
     16        (WebCore::EmptyStorageNamespaceProvider::createLocalStorageNamespace):
     17        (WebCore::EmptyStorageNamespaceProvider::createTransientLocalStorageNamespace):
     18        (WebCore::EmptyStorageNamespaceProvider::createEphemeralLocalStorageNamespace): Deleted.
     19
     20        * page/Chrome.cpp:
     21        (WebCore::Chrome::createWindow const): ephemeral localStorage of different windows will connect to the same
     22        StorageArea in network process, so no need to copy from parent window to child window.
     23
     24        * page/DOMWindow.cpp:
     25        (WebCore::DOMWindow::prewarmLocalStorageIfNecessary): localStorage will be prewarmed in network process in the
     26        initialization of StorageAreaMap.
     27
     28        * page/Page.cpp:
     29        (WebCore::m_applicationManifest):
     30        (WebCore::Page::~Page):
     31        (WebCore::Page::setSessionID):
     32        (WebCore::Page::ephemeralLocalStorage): Deleted.
     33        (WebCore::Page::setEphemeralLocalStorage): Deleted.
     34        (WebCore::Page::setStorageNamespaceProvider): Deleted.
     35        * page/Page.h:
     36        (WebCore::Page::storageNamespaceProvider):
     37        * storage/Storage.cpp:
     38        (WebCore::Storage::prewarm): Deleted.
     39        * storage/Storage.h:
     40        * storage/StorageArea.h:
     41        (WebCore::StorageArea::closeDatabaseIfIdle):
     42        (WebCore::StorageArea::prewarm): Deleted.
     43        * storage/StorageNamespace.h:
     44        * storage/StorageNamespaceProvider.cpp:
     45        (WebCore::StorageNamespaceProvider::~StorageNamespaceProvider):
     46        (WebCore::StorageNamespaceProvider::localStorageArea):
     47        (WebCore::StorageNamespaceProvider::localStorageNamespace):
     48        (WebCore::StorageNamespaceProvider::transientLocalStorageNamespace):
     49        (WebCore::StorageNamespaceProvider::enableLegacyPrivateBrowsingForTesting): change SessionID of storageNamespace
     50        and update every StorageArea in this namespace.
     51        (WebCore::StorageNamespaceProvider::addPage): Deleted.
     52        (WebCore::StorageNamespaceProvider::removePage): Deleted.
     53        * storage/StorageNamespaceProvider.h:
     54        * storage/StorageType.h:
     55        (WebCore::isLocalStorage):
     56
    1572019-08-15  Saam Barati  <sbarati@apple.com>
    258
  • trunk/Source/WebCore/loader/EmptyClients.cpp

    r247722 r248734  
    391391        StorageType storageType() const final { return StorageType::Local; }
    392392        size_t memoryBytesUsedByCache() final { return 0; }
    393         const SecurityOriginData& securityOrigin() const final { static NeverDestroyed<SecurityOriginData> origin; return origin.get(); }
    394393    };
    395394
    … …  
    397396        Ref<StorageArea> storageArea(const SecurityOriginData&) final { return adoptRef(*new EmptyStorageArea); }
    398397        Ref<StorageNamespace> copy(Page*) final { return adoptRef(*new EmptyStorageNamespace); }
     398        PAL::SessionID sessionID() const { return PAL::SessionID::emptySessionID(); }
     399        void setSessionIDForTesting(PAL::SessionID) { };
    399400    };
    400401
    401402    Ref<StorageNamespace> createSessionStorageNamespace(Page&, unsigned) final;
    402     Ref<StorageNamespace> createLocalStorageNamespace(unsigned) final;
    403     Ref<StorageNamespace> createEphemeralLocalStorageNamespace(Page&, unsigned) final;
    404     Ref<StorageNamespace> createTransientLocalStorageNamespace(SecurityOrigin&, unsigned) final;
     403    Ref<StorageNamespace> createLocalStorageNamespace(unsigned, PAL::SessionID) final;
     404    Ref<StorageNamespace> createTransientLocalStorageNamespace(SecurityOrigin&, unsigned, PAL::SessionID) final;
     405
    405406};
    406407
    … …  
    526527}
    527528
    528 Ref<StorageNamespace> EmptyStorageNamespaceProvider::createLocalStorageNamespace(unsigned)
     529Ref<StorageNamespace> EmptyStorageNamespaceProvider::createLocalStorageNamespace(unsigned, PAL::SessionID)
    529530{
    530531    return adoptRef(*new EmptyStorageNamespace);
    531532}
    532533
    533 Ref<StorageNamespace> EmptyStorageNamespaceProvider::createEphemeralLocalStorageNamespace(Page&, unsigned)
    534 {
    535     return adoptRef(*new EmptyStorageNamespace);
    536 }
    537 
    538 Ref<StorageNamespace> EmptyStorageNamespaceProvider::createTransientLocalStorageNamespace(SecurityOrigin&, unsigned)
     534Ref<StorageNamespace> EmptyStorageNamespaceProvider::createTransientLocalStorageNamespace(SecurityOrigin&, unsigned, PAL::SessionID)
    539535{
    540536    return adoptRef(*new EmptyStorageNamespace);
  • trunk/Source/WebCore/page/Chrome.cpp

    r248139 r248734  
    190190    if (auto* oldSessionStorage = m_page.sessionStorage(false))
    191191        newPage->setSessionStorage(oldSessionStorage->copy(newPage));
    192     if (auto* oldEphemeralLocalStorage = m_page.ephemeralLocalStorage(false))
    193         newPage->setEphemeralLocalStorage(oldEphemeralLocalStorage->copy(newPage));
    194192
    195193    return newPage;
  • trunk/Source/WebCore/page/DOMWindow.cpp

    r248491 r248734  
    443443        return;
    444444
    445     if (localStorage->prewarm())
    446         page->mainFrame().didPrewarmLocalStorage();
     445    page->mainFrame().didPrewarmLocalStorage();
    447446}
    448447
  • trunk/Source/WebCore/page/Page.cpp

    r248667 r248734  
    290290
    291291    m_pluginInfoProvider->addPage(*this);
    292     m_storageNamespaceProvider->addPage(*this);
    293292    m_userContentProvider->addPage(*this);
    294293    m_visitedLinkStore->addPage(*this);
    … …  
    368367
    369368    m_pluginInfoProvider->removePage(*this);
    370     m_storageNamespaceProvider->removePage(*this);
    371369    m_userContentProvider->removePage(*this);
    372370    m_visitedLinkStore->removePage(*this);
    … …  
    15091507{
    15101508    m_sessionStorage = WTFMove(newStorage);
    1511 }
    1512 
    1513 StorageNamespace* Page::ephemeralLocalStorage(bool optionalCreate)
    1514 {
    1515     if (!m_ephemeralLocalStorage && optionalCreate)
    1516         m_ephemeralLocalStorage = m_storageNamespaceProvider->createEphemeralLocalStorageNamespace(*this, m_settings->sessionStorageQuota());
    1517 
    1518     return m_ephemeralLocalStorage.get();
    1519 }
    1520 
    1521 void Page::setEphemeralLocalStorage(RefPtr<StorageNamespace>&& newStorage)
    1522 {
    1523     m_ephemeralLocalStorage = WTFMove(newStorage);
    15241509}
    15251510
    … …  
    24712456}
    24722457
    2473 void Page::setStorageNamespaceProvider(Ref<StorageNamespaceProvider>&& storageNamespaceProvider)
    2474 {
    2475     m_storageNamespaceProvider->removePage(*this);
    2476     m_storageNamespaceProvider = WTFMove(storageNamespaceProvider);
    2477     m_storageNamespaceProvider->addPage(*this);
    2478 
    2479     // This needs to reset all the local storage namespaces of all the pages.
    2480 }
    2481 
    24822458VisitedLinkStore& Page::visitedLinkStore()
    24832459{
    … …  
    25072483        m_idbConnectionToServer = nullptr;
    25082484#endif
     2485
     2486    if (sessionID != m_sessionID && m_sessionStorage)
     2487        m_sessionStorage->setSessionIDForTesting(sessionID);
    25092488
    25102489    bool privateBrowsingStateChanged = (sessionID.isEphemeral() != m_sessionID.isEphemeral());
  • trunk/Source/WebCore/page/Page.h

    r247667 r248734  
    508508    void setSessionStorage(RefPtr<StorageNamespace>&&);
    509509
    510     StorageNamespace* ephemeralLocalStorage(bool optionalCreate = true);
    511     void setEphemeralLocalStorage(RefPtr<StorageNamespace>&&);
    512 
    513510    bool hasCustomHTMLTokenizerTimeDelay() const;
    514511    double customHTMLTokenizerTimeDelay() const;
    … …  
    600597
    601598    StorageNamespaceProvider& storageNamespaceProvider() { return m_storageNamespaceProvider.get(); }
    602     void setStorageNamespaceProvider(Ref<StorageNamespaceProvider>&&);
    603599
    604600    PluginInfoProvider& pluginInfoProvider();
    … …  
    878874
    879875    RefPtr<StorageNamespace> m_sessionStorage;
    880     RefPtr<StorageNamespace> m_ephemeralLocalStorage;
    881876
    882877    TimerThrottlingState m_timerThrottlingState { TimerThrottlingState::Disabled };
  • trunk/Source/WebCore/storage/Storage.cpp

    r247555 r248734  
    9898}
    9999
    100 bool Storage::prewarm()
    101 {
    102     return m_storageArea->prewarm();
    103 }
    104 
    105100ExceptionOr<void> Storage::clear()
    106101{
  • trunk/Source/WebCore/storage/Storage.h

    r247555 r248734  
    4747    ExceptionOr<void> clear();
    4848    bool contains(const String& key) const;
    49     bool prewarm();
    5049
    5150    // Bindings support functions.
  • trunk/Source/WebCore/storage/StorageArea.h

    r247555 r248734  
    5959    virtual void decrementAccessCount() { }
    6060    virtual void closeDatabaseIfIdle() { }
    61     virtual bool prewarm() { return false; }
    62 
    63     virtual const SecurityOriginData& securityOrigin() const = 0;
    6461};
    6562
  • trunk/Source/WebCore/storage/StorageNamespace.h

    r239535 r248734  
    2929#include <wtf/RefCounted.h>
    3030
     31namespace PAL {
     32class SessionID;
     33}
     34
    3135namespace WebCore {
    3236
    … …  
    4044    virtual Ref<StorageArea> storageArea(const SecurityOriginData&) = 0;
    4145    virtual Ref<StorageNamespace> copy(Page* newPage) = 0;
     46
     47    virtual PAL::SessionID sessionID() const = 0;
     48    virtual void setSessionIDForTesting(PAL::SessionID) = 0;
    4249};
    4350
  • trunk/Source/WebCore/storage/StorageNamespaceProvider.cpp

    r239535 r248734  
    4444StorageNamespaceProvider::~StorageNamespaceProvider()
    4545{
    46     ASSERT(m_pages.isEmpty());
    47 }
    48 
    49 void StorageNamespaceProvider::addPage(Page& page)
    50 {
    51     ASSERT(!m_pages.contains(&page));
    52 
    53     m_pages.add(&page);
    54 }
    55 
    56 void StorageNamespaceProvider::removePage(Page& page)
    57 {
    58     ASSERT(m_pages.contains(&page));
    59 
    60     m_pages.remove(&page);
    6146}
    6247
    … …  
    6752    ASSERT(document.page());
    6853
    69     bool ephemeral = document.page()->usesEphemeralSession();
    7054    bool transient = !document.securityOrigin().canAccessLocalStorage(&document.topOrigin());
    7155
    … …  
    7357
    7458    if (transient)
    75         storageNamespace = &transientLocalStorageNamespace(document.topOrigin());
    76     else if (ephemeral)
    77         storageNamespace = document.page()->ephemeralLocalStorage();
     59        storageNamespace = &transientLocalStorageNamespace(document.topOrigin(), document.page()->sessionID());
    7860    else
    79         storageNamespace = &localStorageNamespace();
     61        storageNamespace = &localStorageNamespace(document.page()->sessionID());
    8062
    8163    return storageNamespace->storageArea(document.securityOrigin().data());
    8264}
    8365
    84 StorageNamespace& StorageNamespaceProvider::localStorageNamespace()
     66StorageNamespace& StorageNamespaceProvider::localStorageNamespace(PAL::SessionID sessionID)
    8567{
    8668    if (!m_localStorageNamespace)
    87         m_localStorageNamespace = createLocalStorageNamespace(localStorageDatabaseQuotaInBytes);
     69        m_localStorageNamespace = createLocalStorageNamespace(localStorageDatabaseQuotaInBytes, sessionID);
    8870
     71    ASSERT(m_localStorageNamespace->sessionID() == sessionID);
    8972    return *m_localStorageNamespace;
    9073}
    9174
    92 StorageNamespace& StorageNamespaceProvider::transientLocalStorageNamespace(SecurityOrigin& securityOrigin)
     75StorageNamespace& StorageNamespaceProvider::transientLocalStorageNamespace(SecurityOrigin& securityOrigin, PAL::SessionID sessionID)
    9376{
    94     auto& slot = m_transientLocalStorageMap.add(&securityOrigin, nullptr).iterator->value;
     77    auto& slot = m_transientLocalStorageNamespaces.add(securityOrigin.data(), nullptr).iterator->value;
    9578    if (!slot)
    96         slot = createTransientLocalStorageNamespace(securityOrigin, localStorageDatabaseQuotaInBytes);
     79        slot = createTransientLocalStorageNamespace(securityOrigin, localStorageDatabaseQuotaInBytes, sessionID);
    9780
     81    ASSERT(slot->sessionID() == sessionID);
    9882    return *slot;
    9983}
    10084
     85void StorageNamespaceProvider::enableLegacyPrivateBrowsingForTesting(bool enabled)
     86{
     87    auto newSessionID = enabled ? PAL::SessionID::legacyPrivateSessionID() : PAL::SessionID::defaultSessionID();
     88    if (m_localStorageNamespace && newSessionID != m_localStorageNamespace->sessionID())
     89        m_localStorageNamespace->setSessionIDForTesting(newSessionID);
     90   
     91    for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values()) {
     92        if (newSessionID != transientLocalStorageNamespace->sessionID())
     93            m_localStorageNamespace->setSessionIDForTesting(newSessionID);
     94    }
    10195}
     96
     97}
  • trunk/Source/WebCore/storage/StorageNamespaceProvider.h

    r239535 r248734  
    3232#include <wtf/RefCounted.h>
    3333
     34namespace PAL {
     35class SessionID;
     36}
     37
    3438namespace WebCore {
    3539
    … …  
    4650
    4751    virtual Ref<StorageNamespace> createSessionStorageNamespace(Page&, unsigned quota) = 0;
    48     virtual Ref<StorageNamespace> createEphemeralLocalStorageNamespace(Page&, unsigned quota) = 0;
    4952
    5053    Ref<StorageArea> localStorageArea(Document&);
    5154
    52     void addPage(Page&);
    53     void removePage(Page&);
     55    WEBCORE_EXPORT void enableLegacyPrivateBrowsingForTesting(bool enabled);
    5456
    5557protected:
    … …  
    5759
    5860private:
    59     StorageNamespace& localStorageNamespace();
    60     StorageNamespace& transientLocalStorageNamespace(SecurityOrigin&);
     61    StorageNamespace& localStorageNamespace(PAL::SessionID);
     62    StorageNamespace& transientLocalStorageNamespace(SecurityOrigin&, PAL::SessionID);
    6163
    62     virtual Ref<StorageNamespace> createLocalStorageNamespace(unsigned quota) = 0;
    63     virtual Ref<StorageNamespace> createTransientLocalStorageNamespace(SecurityOrigin&, unsigned quota) = 0;
    64 
    65     HashSet<Page*> m_pages;
     64    virtual Ref<StorageNamespace> createLocalStorageNamespace(unsigned quota, PAL::SessionID) = 0;
     65    virtual Ref<StorageNamespace> createTransientLocalStorageNamespace(SecurityOrigin&, unsigned quota, PAL::SessionID) = 0;
    6666
    6767    RefPtr<StorageNamespace> m_localStorageNamespace;
    68     HashMap<RefPtr<SecurityOrigin>, RefPtr<StorageNamespace>> m_transientLocalStorageMap;
     68    HashMap<SecurityOriginData, RefPtr<StorageNamespace>> m_transientLocalStorageNamespaces;
    6969};
    7070
  • trunk/Source/WebCore/storage/StorageType.h

    r215315 r248734  
    3131    Session,
    3232    Local,
    33     EphemeralLocal,
    3433    TransientLocal,
    3534};
    … …  
    3736inline bool isLocalStorage(StorageType storageType)
    3837{
    39     return storageType == StorageType::Local || storageType == StorageType::TransientLocal || storageType == StorageType::EphemeralLocal;
     38    return storageType == StorageType::Local || storageType == StorageType::TransientLocal;
    4039}
    4140
  • trunk/Source/WebKit/CMakeLists.txt

    r246388 r248734  
    119119    NetworkProcess/ServiceWorker/WebSWServerToContextConnection.messages.in
    120120
    121     NetworkProcess/WebStorage/StorageManager.messages.in
     121    NetworkProcess/WebStorage/StorageManagerSet.messages.in
    122122
    123123    NetworkProcess/cache/CacheStorageEngineConnection.messages.in
  • trunk/Source/WebKit/ChangeLog

    r248733 r248734  
     12019-08-15  Sihui Liu  <sihui_liu@apple.com>
     2
     3        Some improvements on web storage
     4        https://bugs.webkit.org/show_bug.cgi?id=200373
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        Fix some issues in web storage architecture. For example, sessionStorageNameSpace for web page is prepared and
     9        destroyed in the network process when the page comes and goes, even though the page may not use sessionStorage
     10        at all. The messages about page state sent from web process to network process can be waste.
     11
     12        Here are some general ideas of this patch:
     13        1. Network process owns the web storage, and web process keeps a small local copy (based on session and
     14        origins that are visited). There is a virtual connection from the local copy in the web process to the original
     15        copy in the network process. The connection is created by web process when some page asks for web storage.
     16        2. If connection is lost because network process is gone, storage in memory will be lost. The local copy in web
     17        processs will be discarded.
     18        3. (SessionID, StorageNamespaceID, SecurityOrigin) is used to identify a storage area. If session is changed in
     19        web process (like enabling private browsing in layout test now), a re-connection with different sessionID would
     20        suffice to load another copy of storage.
     21        4. localStorage in ephemeral session has the same behavior as localStorage instead of sessionStorage, which
     22        means different pages in the same ephemeral session share the same localStorage.
     23
     24        Also, this patch introduces StorageManagerSet to network process. It handles web storage stuff, including
     25        receiving storage messages from web process, on one background thread. Previously each session has its own
     26        StorageManager and each StorageManager has its own WorkQueue.
     27
     28        * CMakeLists.txt:
     29        * DerivedSources-input.xcfilelist:
     30        * DerivedSources-output.xcfilelist:
     31        * DerivedSources.make:
     32
     33        * NetworkProcess/NetworkConnectionToWebProcess.cpp: remove message handlers that are no longer needed. Network
     34        process no longer needs to know page states from web process.
     35        (WebKit::NetworkConnectionToWebProcess::didClose):
     36        (WebKit::NetworkConnectionToWebProcess::webPageWasAdded): Deleted.
     37        (WebKit::NetworkConnectionToWebProcess::webPageWasRemoved): Deleted.
     38        (WebKit::NetworkConnectionToWebProcess::webProcessSessionChanged): Deleted.
     39        * NetworkProcess/NetworkConnectionToWebProcess.h:
     40        * NetworkProcess/NetworkConnectionToWebProcess.messages.in:
     41
     42        * NetworkProcess/NetworkProcess.cpp: NetworkProcess uses StorageManagerSet instead of StorageManager from
     43        different sessions to deal with web storage.
     44        (WebKit::NetworkProcess::NetworkProcess):
     45        (WebKit::NetworkProcess::initializeNetworkProcess):
     46        (WebKit::NetworkProcess::createNetworkConnectionToWebProcess): StorageManagerSet starts handling
     47        StorageManagerSet messages from the new connection.
     48        (WebKit::NetworkProcess::addWebsiteDataStore):
     49        (WebKit::NetworkProcess::destroySession):
     50        (WebKit::NetworkProcess::hasLocalStorage):
     51        (WebKit::NetworkProcess::fetchWebsiteData):
     52        (WebKit::NetworkProcess::deleteWebsiteData):
     53        (WebKit::NetworkProcess::deleteWebsiteDataForOrigins):
     54        (WebKit::NetworkProcess::deleteWebsiteDataForRegistrableDomains):
     55        (WebKit::NetworkProcess::actualPrepareToSuspend):
     56        (WebKit::NetworkProcess::resume):
     57        (WebKit::NetworkProcess::syncLocalStorage):
     58        (WebKit::NetworkProcess::clearLegacyPrivateBrowsingLocalStorage): added for clearing in-memory ephemeral
     59        localStorage.
     60        (WebKit::NetworkProcess::getLocalStorageOriginDetails):
     61        (WebKit::NetworkProcess::connectionToWebProcessClosed):
     62        (WebKit::NetworkProcess::webPageWasAdded): Deleted.
     63        (WebKit::NetworkProcess::webPageWasRemoved): Deleted.
     64        (WebKit::NetworkProcess::webProcessWasDisconnected): Deleted.
     65        (WebKit::NetworkProcess::webProcessSessionChanged): Deleted.
     66        * NetworkProcess/NetworkProcess.h:
     67        * NetworkProcess/NetworkProcess.messages.in:
     68
     69        * NetworkProcess/NetworkSession.cpp: StorageManager is moved out of NetworkSession. It is now managed by
     70        StorageManagerSet.
     71        (WebKit::NetworkSession::NetworkSession):
     72        (WebKit::NetworkSession::~NetworkSession):
     73        * NetworkProcess/NetworkSession.h:
     74        (WebKit::NetworkSession::storageManager): Deleted.
     75
     76        * NetworkProcess/NetworkSessionCreationParameters.cpp: creation parameters of StorageManager is moved out of
     77        NetworkSessionCreationParameters.
     78        (WebKit::NetworkSessionCreationParameters::privateSessionParameters):
     79        (WebKit::NetworkSessionCreationParameters::encode const):
     80        (WebKit::NetworkSessionCreationParameters::decode):
     81        * NetworkProcess/NetworkSessionCreationParameters.h:
     82
     83        * NetworkProcess/WebStorage/LocalStorageDatabase.cpp:
     84        (WebKit::LocalStorageDatabase::updateDatabase): remove an assertion that is no longer true as we can force an
     85        update with syncLocalStorage now.
     86        * NetworkProcess/WebStorage/LocalStorageDatabase.h: make updateDatabase public for syncLocalStorage.
     87
     88        * NetworkProcess/WebStorage/LocalStorageDatabaseTracker.cpp: LocalStorageDatabaseTracker is created on the
     89        background thread now, so it does not hold WorkQueue to do the file operation.
     90        (WebKit::LocalStorageDatabaseTracker::create):
     91        (WebKit::LocalStorageDatabaseTracker::LocalStorageDatabaseTracker):
     92        (WebKit::LocalStorageDatabaseTracker::~LocalStorageDatabaseTracker):
     93        * NetworkProcess/WebStorage/LocalStorageDatabaseTracker.h:
     94        * NetworkProcess/WebStorage/LocalStorageNamespace.cpp:
     95        (WebKit::LocalStorageNamespace::getOrCreateStorageArea):
     96        (WebKit::LocalStorageNamespace::cloneTo): Deleted.
     97        * NetworkProcess/WebStorage/LocalStorageNamespace.h:
     98        * NetworkProcess/WebStorage/SessionStorageNamespace.cpp:
     99        (WebKit::SessionStorageNamespace::getOrCreateStorageArea):
     100        (WebKit::SessionStorageNamespace::addAllowedConnection): Deleted.
     101        (WebKit::SessionStorageNamespace::removeAllowedConnection): Deleted.
     102        * NetworkProcess/WebStorage/SessionStorageNamespace.h:
     103        (WebKit::SessionStorageNamespace::allowedConnections const): Deleted.
     104
     105        * NetworkProcess/WebStorage/StorageArea.cpp:
     106        (WebKit::generateStorageAreaIdentifier): each StorageArea has an identifier. StorageAreaMap in web process uses
     107        this identifier to indicate which StorageArea it is connecting to.
     108        (WebKit::StorageArea::StorageArea):
     109        (WebKit::StorageArea::~StorageArea): StorageArea may still have listeners because StorageArea should be
     110        destroyed by requests from UI process, and listeners are connections to web processses.
     111        (WebKit::StorageArea::addListener): load localStorageDatabase in advance if there is some connection to this
     112        LocalStorage area.
     113        (WebKit::StorageArea::removeListener):
     114        (WebKit::StorageArea::hasListener const):
     115        (WebKit::StorageArea::clear):
     116        (WebKit::StorageArea::openDatabaseAndImportItemsIfNeeded const):
     117        (WebKit::StorageArea::dispatchEvents const):
     118        (WebKit::StorageArea::syncToDatabase):
     119        (WebKit::StorageArea::setItems): Deleted. Stop syncing from web process to network process after network process
     120        is relaunched.
     121        * NetworkProcess/WebStorage/StorageArea.h:
     122        (WebKit::StorageArea::identifier):
     123        (WebKit::StorageArea::setWorkQueue):
     124
     125        * NetworkProcess/WebStorage/StorageManager.cpp: StorageManager should be accessed by only background thread now.
     126        (WebKit::StorageManager::StorageManager):
     127        (WebKit::StorageManager::~StorageManager):
     128        (WebKit::StorageManager::createSessionStorageNamespace):
     129        (WebKit::StorageManager::destroySessionStorageNamespace): this is not used now but keep it for future
     130        improvement to remove in-memory sessionStorage in network process if we know some web page is gone forever.
     131        (WebKit::StorageManager::cloneSessionStorageNamespace): previously each page had its own ephemeral
     132        localStorageNamespace and now all pages in the same session share one localStorage, so we don't need to clone
     133        localStorageNamespace.
     134        (WebKit::StorageManager::getSessionStorageOrigins):
     135        (WebKit::StorageManager::deleteSessionStorageOrigins):
     136        (WebKit::StorageManager::deleteSessionStorageEntriesForOrigins):
     137        (WebKit::StorageManager::getLocalStorageOrigins):
     138        (WebKit::StorageManager::getLocalStorageOriginDetails):
     139        (WebKit::StorageManager::deleteLocalStorageOriginsModifiedSince):
     140        (WebKit::StorageManager::deleteLocalStorageEntriesForOrigins):
     141        (WebKit::StorageManager::createLocalStorageArea):
     142        (WebKit::StorageManager::createTransientLocalStorageArea):
     143        (WebKit::StorageManager::createSessionStorageArea):
     144        (WebKit::StorageManager::getOrCreateLocalStorageNamespace):
     145        (WebKit::StorageManager::getOrCreateTransientLocalStorageNamespace):
     146        (WebKit::StorageManager::getOrCreateSessionStorageNamespace):
     147        (WebKit::StorageManager::clearStorageNamespaces):
     148        (WebKit::StorageManager::addAllowedSessionStorageNamespaceConnection): Deleted.
     149        (WebKit::StorageManager::removeAllowedSessionStorageNamespaceConnection): Deleted.
     150        (WebKit::StorageManager::processDidCloseConnection): Deleted.
     151        (WebKit::StorageManager::deleteLocalStorageEntriesForOrigin): Deleted.
     152        (WebKit::StorageManager::createLocalStorageMap): Deleted.
     153        (WebKit::StorageManager::createTransientLocalStorageMap): Deleted.
     154        (WebKit::StorageManager::createSessionStorageMap): Deleted.
     155        (WebKit::StorageManager::destroyStorageMap): Deleted.
     156        (WebKit::StorageManager::prewarm): Deleted.
     157        (WebKit::StorageManager::getValues): Deleted.
     158        (WebKit::StorageManager::setItem): Deleted.
     159        (WebKit::StorageManager::setItems): Deleted.
     160        (WebKit::StorageManager::removeItem): Deleted.
     161        (WebKit::StorageManager::clear): Deleted.
     162        (WebKit::StorageManager::waitUntilTasksFinished): Deleted.
     163        (WebKit::StorageManager::suspend): Deleted.
     164        (WebKit::StorageManager::resume): Deleted.
     165        (WebKit::StorageManager::findStorageArea const): Deleted.
     166        * NetworkProcess/WebStorage/StorageManager.h:
     167        (WebKit::StorageManager::workQueue const): Deleted.
     168        (): Deleted.
     169
     170        * NetworkProcess/WebStorage/StorageManager.messages.in: Removed. Moved to StorageManagerSet.messages.in.
     171
     172        * NetworkProcess/WebStorage/StorageManagerSet.cpp: Added.
     173        (WebKit::StorageManagerSet::create):
     174        (WebKit::StorageManagerSet::StorageManagerSet):
     175        (WebKit::StorageManagerSet::~StorageManagerSet):
     176        (WebKit::StorageManagerSet::add):
     177        (WebKit::StorageManagerSet::remove):
     178        (WebKit::StorageManagerSet::contains):
     179        (WebKit::StorageManagerSet::addConnection):
     180        (WebKit::StorageManagerSet::removeConnection):
     181        (WebKit::StorageManagerSet::waitUntilTasksFinished):
     182        (WebKit::StorageManagerSet::waitUntilSyncingLocalStorageFinished):
     183        (WebKit::StorageManagerSet::suspend):
     184        (WebKit::StorageManagerSet::resume):
     185        (WebKit::StorageManagerSet::getSessionStorageOrigins):
     186        (WebKit::StorageManagerSet::deleteSessionStorage):
     187        (WebKit::StorageManagerSet::deleteSessionStorageForOrigins):
     188        (WebKit::StorageManagerSet::getLocalStorageOrigins):
     189        (WebKit::StorageManagerSet::deleteLocalStorageModifiedSince):
     190        (WebKit::StorageManagerSet::deleteLocalStorageForOrigins):
     191        (WebKit::StorageManagerSet::getLocalStorageOriginDetails):
     192        (WebKit::StorageManagerSet::connectToLocalStorageArea):
     193        (WebKit::StorageManagerSet::connectToTransientLocalStorageArea):
     194        (WebKit::StorageManagerSet::connectToSessionStorageArea):
     195        (WebKit::StorageManagerSet::disconnectFromStorageArea):
     196        (WebKit::StorageManagerSet::getValues):
     197        (WebKit::StorageManagerSet::setItem):
     198        (WebKit::StorageManagerSet::removeItem):
     199        (WebKit::StorageManagerSet::clear):
     200        (WebKit::StorageManagerSet::cloneSessionStorageNamespace):
     201        * NetworkProcess/WebStorage/StorageManagerSet.h: Added.
     202        * NetworkProcess/WebStorage/StorageManagerSet.messages.in: Added.
     203
     204        * Shared/WebsiteDataStoreParameters.cpp: creation parameters of StorageManager are moved to
     205        WebsiteDataStoreParameters.
     206        (WebKit::WebsiteDataStoreParameters::encode const):
     207        (WebKit::WebsiteDataStoreParameters::decode):
     208        (WebKit::WebsiteDataStoreParameters::privateSessionParameters):
     209        * Shared/WebsiteDataStoreParameters.h:
     210        * Sources.txt:
     211
     212        * UIProcess/API/C/WKContext.cpp: add SPI for tests.
     213        (WKContextSyncLocalStorage):
     214        (WKContextClearLegacyPrivateBrowsingLocalStorage):
     215        * UIProcess/API/C/WKContextPrivate.h:
     216        * UIProcess/API/C/WKWebsiteDataStoreRef.cpp:
     217        (WKWebsiteDataStoreRemoveLocalStorage):
     218        * UIProcess/API/C/WKWebsiteDataStoreRef.h:
     219        * UIProcess/WebProcessPool.cpp:
     220        (WebKit::WebProcessPool::ensureNetworkProcess):
     221        (WebKit::WebProcessPool::syncLocalStorage):
     222        (WebKit::WebProcessPool::clearLegacyPrivateBrowsingLocalStorage):
     223        * UIProcess/WebProcessPool.h:
     224        * UIProcess/WebsiteData/Cocoa/WebsiteDataStoreCocoa.mm:
     225        (WebKit::WebsiteDataStore::parameters):
     226        * UIProcess/WebsiteData/WebsiteDataStore.cpp:
     227        (WebKit::WebsiteDataStore::parameters):
     228        * WebKit.xcodeproj/project.pbxproj:
     229
     230        * WebProcess/InjectedBundle/InjectedBundle.cpp: session change of web storage is done via
     231        WebStorageNamespaceProvider instead of WebProcess now.
     232        (WebKit::InjectedBundle::setPrivateBrowsingEnabled):
     233        * WebProcess/WebProcess.cpp: web process no longer sends messsages about page state to network process.
     234        (WebKit::WebProcess::createWebPage):
     235        (WebKit::WebProcess::removeWebPage):
     236        (WebKit::WebProcess::ensureNetworkProcessConnection):
     237        (WebKit::WebProcess::networkProcessConnectionClosed):
     238        (WebKit::WebProcess::storageAreaMap const):
     239        (WebKit::WebProcess::enablePrivateBrowsingForTesting): Deleted. This was used for changing session via
     240        WebProcess.
     241        * WebProcess/WebProcess.h:
     242        * WebProcess/WebStorage/StorageAreaImpl.cpp:
     243        (WebKit::StorageAreaImpl::StorageAreaImpl):
     244        (WebKit::StorageAreaImpl::length):
     245        (WebKit::StorageAreaImpl::key):
     246        (WebKit::StorageAreaImpl::item):
     247        (WebKit::StorageAreaImpl::setItem):
     248        (WebKit::StorageAreaImpl::removeItem):
     249        (WebKit::StorageAreaImpl::clear):
     250        (WebKit::StorageAreaImpl::contains):
     251        (WebKit::StorageAreaImpl::storageType const):
     252        (WebKit::StorageAreaImpl::incrementAccessCount):
     253        (WebKit::StorageAreaImpl::decrementAccessCount):
     254        (WebKit::StorageAreaImpl::prewarm): Deleted.
     255        (WebKit::StorageAreaImpl::securityOrigin const): Deleted.
     256
     257        * WebProcess/WebStorage/StorageAreaImpl.h: make StorageAreaImpl hold a weak reference to StorageAreaMap and
     258        StorageNamespaceImpl hold a strong reference. In this way lifeime of localStorage StorageAreraMap stays align
     259        with StorageNameSpaceProvider and Page.
     260
     261        * WebProcess/WebStorage/StorageAreaMap.cpp: identifier of StorageAreaMap is the same as identifier of
     262        StorageArea it connects to. If the identifier is 0, it means the StorageAreaMap is disconnected.
     263        (WebKit::StorageAreaMap::StorageAreaMap):
     264        (WebKit::StorageAreaMap::~StorageAreaMap):
     265        (WebKit::StorageAreaMap::setItem):
     266        (WebKit::StorageAreaMap::removeItem):
     267        (WebKit::StorageAreaMap::clear):
     268        (WebKit::StorageAreaMap::resetValues):
     269        (WebKit::StorageAreaMap::loadValuesIfNeeded):
     270        (WebKit::StorageAreaMap::applyChange):
     271        (WebKit::StorageAreaMap::dispatchStorageEvent):
     272        (WebKit::StorageAreaMap::dispatchSessionStorageEvent):
     273        (WebKit::StorageAreaMap::dispatchLocalStorageEvent):
     274        (WebKit::StorageAreaMap::connect):
     275        (WebKit::StorageAreaMap::disconnect):
     276        (WebKit::generateStorageMapID): Deleted.
     277        (WebKit::StorageAreaMap::prewarm): Deleted.
     278        (WebKit::StorageAreaMap::didGetValues): Deleted. This is useless as GetValues is a synchronous operation.
     279        * WebProcess/WebStorage/StorageAreaMap.h:
     280        (): Deleted.
     281
     282        * WebProcess/WebStorage/StorageAreaMap.messages.in: there are two synchronous messages, one for connection and
     283        one for getting values. We may merge them into one in future improvement.
     284        * WebProcess/WebStorage/StorageNamespaceImpl.cpp:
     285        (WebKit::StorageNamespaceImpl::createSessionStorageNamespace):
     286        (WebKit::StorageNamespaceImpl::createLocalStorageNamespace):
     287        (WebKit::StorageNamespaceImpl::createTransientLocalStorageNamespace):
     288        (WebKit::StorageNamespaceImpl::StorageNamespaceImpl):
     289        (WebKit::StorageNamespaceImpl::storageArea):
     290        (WebKit::StorageNamespaceImpl::copy):
     291        (WebKit::StorageNamespaceImpl::setSessionIDForTesting):
     292        (WebKit::StorageNamespaceImpl::createEphemeralLocalStorageNamespace): Deleted.
     293        * WebProcess/WebStorage/StorageNamespaceImpl.h:
     294        * WebProcess/WebStorage/WebStorageNamespaceProvider.cpp:
     295        (WebKit::WebStorageNamespaceProvider::createSessionStorageNamespace):
     296        (WebKit::WebStorageNamespaceProvider::createLocalStorageNamespace):
     297        (WebKit::WebStorageNamespaceProvider::createTransientLocalStorageNamespace):
     298        (WebKit::WebStorageNamespaceProvider::createEphemeralLocalStorageNamespace): Deleted.
     299        * WebProcess/WebStorage/WebStorageNamespaceProvider.h:
     300
    13012019-08-15  Wenson Hsieh  <wenson_hsieh@apple.com>
    2302
  • trunk/Source/WebKit/DerivedSources-input.xcfilelist

    r246388 r248734  
    2626$(PROJECT_DIR)/NetworkProcess/ServiceWorker/WebSWServerConnection.messages.in
    2727$(PROJECT_DIR)/NetworkProcess/ServiceWorker/WebSWServerToContextConnection.messages.in
    28 $(PROJECT_DIR)/NetworkProcess/WebStorage/StorageManager.messages.in
     28$(PROJECT_DIR)/NetworkProcess/WebStorage/StorageManagerSet.messages.in
    2929$(PROJECT_DIR)/NetworkProcess/cache/CacheStorageEngineConnection.messages.in
    3030$(PROJECT_DIR)/NetworkProcess/mac/com.apple.WebKit.NetworkProcess.sb.in
    … …  
    8484$(PROJECT_DIR)/UIProcess/WebProcessPool.messages.in
    8585$(PROJECT_DIR)/UIProcess/WebProcessProxy.messages.in
    86 $(PROJECT_DIR)/UIProcess/WebStorage/StorageManager.messages.in
    8786$(PROJECT_DIR)/UIProcess/ios/EditableImageController.messages.in
    8887$(PROJECT_DIR)/UIProcess/ios/SmartMagnificationController.messages.in
  • trunk/Source/WebKit/DerivedSources-output.xcfilelist

    r246388 r248734  
    8989$(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/StorageAreaMapMessageReceiver.cpp
    9090$(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/StorageAreaMapMessages.h
    91 $(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/StorageManagerMessageReceiver.cpp
    92 $(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/StorageManagerMessages.h
     91$(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/StorageManagerSetMessageReceiver.cpp
     92$(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/StorageManagerSetMessages.h
    9393$(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/TextCheckingControllerProxyMessageReceiver.cpp
    9494$(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit2/TextCheckingControllerProxyMessages.h
  • trunk/Source/WebKit/DerivedSources.make

    r246388 r248734  
    137137    SmartMagnificationController \
    138138    StorageAreaMap \
    139     StorageManager \
     139    StorageManagerSet \
    140140    TextCheckingControllerProxy \
    141141    UserMediaCaptureManager \
  • trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.cpp

    r248713 r248734  
    5050#include "PreconnectTask.h"
    5151#include "ServiceWorkerFetchTaskMessages.h"
    52 #include "StorageManager.h"
    5352#include "WebCoreArgumentCoders.h"
    5453#include "WebErrors.h"
    … …  
    300299    stopAllNetworkActivityTracking();
    301300
    302     m_networkProcess->webProcessWasDisconnected(connection);
     301    m_networkProcess->connectionToWebProcessClosed(connection);
    303302
    304303    m_networkProcess->removeNetworkConnectionToWebProcess(*this);
    … …  
    916915#endif
    917916
    918 void NetworkConnectionToWebProcess::webPageWasAdded(PAL::SessionID sessionID, PageIdentifier pageID, WebCore::PageIdentifier oldPageID)
    919 {
    920     m_networkProcess->webPageWasAdded(m_connection.get(), sessionID, pageID, oldPageID);
    921 }
    922 
    923 void NetworkConnectionToWebProcess::webPageWasRemoved(PAL::SessionID sessionID, PageIdentifier pageID)
    924 {
    925     m_networkProcess->webPageWasRemoved(m_connection.get(), sessionID, pageID);
    926 }
    927 
    928 void NetworkConnectionToWebProcess::webProcessSessionChanged(PAL::SessionID newSessionID, const Vector<PageIdentifier>& pages)
    929 {
    930     m_networkProcess->webProcessSessionChanged(m_connection.get(), newSessionID, pages);
    931 }
    932 
    933917} // namespace WebKit
  • trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.h

    r248713 r248734  
    142142    Vector<RefPtr<WebCore::BlobDataFileReference>> resolveBlobReferences(const NetworkResourceLoadParameters&);
    143143
    144     void webPageWasAdded(PAL::SessionID, WebCore::PageIdentifier, WebCore::PageIdentifier oldPageID);
    145     void webPageWasRemoved(PAL::SessionID, WebCore::PageIdentifier);
    146     void webProcessSessionChanged(PAL::SessionID newSessionID, const Vector<WebCore::PageIdentifier>& pages);
    147 
    148144    void removeSocketChannel(uint64_t identifier);
    149145
  • trunk/Source/WebKit/NetworkProcess/NetworkConnectionToWebProcess.messages.in

    r248713 r248734  
    8787    EstablishSWServerConnection(PAL::SessionID sessionID) -> (WebCore::SWServerConnectionIdentifier serverConnectionIdentifier) Synchronous
    8888#endif
    89 
    90     WebPageWasAdded(PAL::SessionID sessionID, WebCore::PageIdentifier pageID, WebCore::PageIdentifier oldPageID)
    91     WebPageWasRemoved(PAL::SessionID sessionID, WebCore::PageIdentifier pageID)
    92     WebProcessSessionChanged(PAL::SessionID newSessionID, Vector<WebCore::PageIdentifier> pages)
    9389}
  • trunk/Source/WebKit/NetworkProcess/NetworkProcess.cpp

    r248699 r248734  
    5454#include "StatisticsData.h"
    5555#include "StorageAccessStatus.h"
    56 #include "StorageManager.h"
    57 #include "StorageManagerMessages.h"
     56#include "StorageManagerSet.h"
    5857#include "WebCookieManager.h"
    5958#include "WebPageProxyMessages.h"
    … …  
    134133NetworkProcess::NetworkProcess(AuxiliaryProcessInitializationParameters&& parameters)
    135134    : m_downloadManager(*this)
     135    , m_storageManagerSet(StorageManagerSet::create())
    136136#if ENABLE(CONTENT_EXTENSIONS)
    137137    , m_networkContentRuleListManager(*this)
    … …  
    337337    initializeStorageQuota(parameters.defaultDataStoreParameters);
    338338
     339    m_storageManagerSet->add(sessionID, parameters.defaultDataStoreParameters.localStorageDirectory, parameters.defaultDataStoreParameters.localStorageDirectoryExtensionHandle);
     340
    339341    auto* defaultSession = networkSession(PAL::SessionID::defaultSessionID());
    340342    auto* defaultStorageSession = defaultSession->networkStorageSession();
    … …  
    448450    UNUSED_PARAM(registrableDomain);
    449451#endif
     452
     453    m_storageManagerSet->addConnection(m_webProcessConnections.last()->connection());
    450454}
    451455
    … …  
    469473        addServiceWorkerSession(parameters.networkSessionParameters.sessionID, parameters.serviceWorkerRegistrationDirectory, parameters.serviceWorkerRegistrationDirectoryExtensionHandle);
    470474#endif
     475
     476    m_storageManagerSet->add(parameters.networkSessionParameters.sessionID, parameters.localStorageDirectory, parameters.localStorageDirectoryExtensionHandle);
    471477
    472478    initializeStorageQuota(parameters);
    … …  
    610616#endif
    611617
     618    m_storageManagerSet->remove(sessionID);
     619
    612620    m_storageQuotaManagers.remove(sessionID);
    613621}
    … …  
    10511059void NetworkProcess::hasLocalStorage(PAL::SessionID sessionID, const RegistrableDomain& domain, CompletionHandler<void(bool)>&& completionHandler)
    10521060{
    1053     if (auto* session = networkSession(sessionID)) {
    1054         session->storageManager().getLocalStorageOrigins([domain, completionHandler = WTFMove(completionHandler)](auto&& origins) mutable {
     1061    if (m_storageManagerSet->contains(sessionID)) {
     1062        m_storageManagerSet->getLocalStorageOrigins(sessionID, [domain, completionHandler = WTFMove(completionHandler)](auto&& origins) mutable {
    10551063            completionHandler(WTF::anyOf(origins, [&domain](auto& origin) {
    10561064                return domain.matches(origin);
    … …  
    13411349    }
    13421350
    1343     auto* session = networkSession(sessionID);
    1344     if (websiteDataTypes.contains(WebsiteDataType::SessionStorage) && session) {
    1345         session->storageManager().getSessionStorageOrigins([callbackAggregator = callbackAggregator.copyRef()](auto&& origins) {
     1351    if (websiteDataTypes.contains(WebsiteDataType::SessionStorage) && m_storageManagerSet->contains(sessionID)) {
     1352        m_storageManagerSet->getSessionStorageOrigins(sessionID, [callbackAggregator = callbackAggregator.copyRef()](auto&& origins) {
    13461353            while (!origins.isEmpty())
    13471354                callbackAggregator->m_websiteData.entries.append(WebsiteData::Entry { origins.takeAny(), WebsiteDataType::SessionStorage, 0 });
    … …  
    13491356    }
    13501357
    1351     if (websiteDataTypes.contains(WebsiteDataType::LocalStorage) && session) {
    1352         session->storageManager().getLocalStorageOrigins([callbackAggregator = callbackAggregator.copyRef()](auto&& origins) {
     1358    if (websiteDataTypes.contains(WebsiteDataType::LocalStorage) && m_storageManagerSet->contains(sessionID)) {
     1359        m_storageManagerSet->getLocalStorageOrigins(sessionID, [callbackAggregator = callbackAggregator.copyRef()](auto&& origins) {
    13531360            while (!origins.isEmpty())
    13541361                callbackAggregator->m_websiteData.entries.append(WebsiteData::Entry { origins.takeAny(), WebsiteDataType::LocalStorage, 0 });
    … …  
    14251432        CacheStorage::Engine::clearAllCaches(*this, sessionID, [clearTasksHandler = clearTasksHandler.copyRef()] { });
    14261433
    1427     auto* session = networkSession(sessionID);
    1428     if (websiteDataTypes.contains(WebsiteDataType::SessionStorage) && session)
    1429         session->storageManager().deleteSessionStorageOrigins([clearTasksHandler = clearTasksHandler.copyRef()] { });
    1430 
    1431     if (websiteDataTypes.contains(WebsiteDataType::LocalStorage) && session)
    1432         session->storageManager().deleteLocalStorageOriginsModifiedSince(modifiedSince, [clearTasksHandler = clearTasksHandler.copyRef()] { });
     1434    if (websiteDataTypes.contains(WebsiteDataType::SessionStorage) && m_storageManagerSet->contains(sessionID))
     1435        m_storageManagerSet->deleteSessionStorage(sessionID, [clearTasksHandler = clearTasksHandler.copyRef()] { });
     1436
     1437    if (websiteDataTypes.contains(WebsiteDataType::LocalStorage) && m_storageManagerSet->contains(sessionID))
     1438        m_storageManagerSet->deleteLocalStorageModifiedSince(sessionID, modifiedSince, [clearTasksHandler = clearTasksHandler.copyRef()] { });
    14331439
    14341440#if ENABLE(INDEXED_DATABASE)
    … …  
    15251531    }
    15261532
    1527     auto* session = networkSession(sessionID);
    1528     if (websiteDataTypes.contains(WebsiteDataType::SessionStorage) && session)
    1529         session->storageManager().deleteSessionStorageEntriesForOrigins(originDatas, [clearTasksHandler = clearTasksHandler.copyRef()] { });
    1530 
    1531     if (websiteDataTypes.contains(WebsiteDataType::LocalStorage) && session)
    1532         session->storageManager().deleteLocalStorageEntriesForOrigins(originDatas, [clearTasksHandler = clearTasksHandler.copyRef()] { });
     1533    if (websiteDataTypes.contains(WebsiteDataType::SessionStorage) && m_storageManagerSet->contains(sessionID))
     1534        m_storageManagerSet->deleteSessionStorageForOrigins(sessionID, originDatas, [clearTasksHandler = clearTasksHandler.copyRef()] { });
     1535
     1536    if (websiteDataTypes.contains(WebsiteDataType::LocalStorage) && m_storageManagerSet->contains(sessionID))
     1537        m_storageManagerSet->deleteLocalStorageForOrigins(sessionID, originDatas, [clearTasksHandler = clearTasksHandler.copyRef()] { });
    15331538
    15341539#if ENABLE(INDEXED_DATABASE)
    … …  
    17271732    }
    17281733
    1729     auto* session = networkSession(sessionID);
    1730     if (session) {
    1731         auto& storageManager = session->storageManager();
     1734    if (m_storageManagerSet->contains(sessionID)) {
    17321735        if (websiteDataTypes.contains(WebsiteDataType::SessionStorage)) {
    1733             storageManager.getSessionStorageOrigins([storageManager = makeRefPtr(storageManager), callbackAggregator = callbackAggregator.copyRef(), domainsToDeleteAllButCookiesFor](auto&& origins) {
     1736            m_storageManagerSet->getSessionStorageOrigins(sessionID, [protectedThis = makeRef(*this), this, sessionID, callbackAggregator = callbackAggregator.copyRef(), domainsToDeleteAllButCookiesFor](auto&& origins) {
    17341737                auto originsToDelete = filterForRegistrableDomains(origins, domainsToDeleteAllButCookiesFor, callbackAggregator->m_domains);
    1735                 storageManager->deleteSessionStorageEntriesForOrigins(originsToDelete, [callbackAggregator = callbackAggregator.copyRef()] { });
     1738                m_storageManagerSet->deleteSessionStorageForOrigins(sessionID, originsToDelete, [callbackAggregator = callbackAggregator.copyRef()] { });
    17361739            });
    17371740        }
    17381741
    17391742        if (websiteDataTypes.contains(WebsiteDataType::LocalStorage)) {
    1740             storageManager.getLocalStorageOrigins([storageManager = makeRefPtr(storageManager), callbackAggregator = callbackAggregator.copyRef(), domainsToDeleteAllButCookiesFor](auto&& origins) {
     1743            m_storageManagerSet->getLocalStorageOrigins(sessionID, [protectedThis = makeRef(*this), this, sessionID, callbackAggregator = callbackAggregator.copyRef(), domainsToDeleteAllButCookiesFor](auto&& origins) {
    17411744                auto originsToDelete = filterForRegistrableDomains(origins, domainsToDeleteAllButCookiesFor, callbackAggregator->m_domains);
    1742                 storageManager->deleteLocalStorageEntriesForOrigins(originsToDelete, [callbackAggregator = callbackAggregator.copyRef()] { });
     1745                m_storageManagerSet->deleteLocalStorageForOrigins(sessionID, originsToDelete, [callbackAggregator = callbackAggregator.copyRef()] { });
    17431746            });
    17441747        }
    … …  
    21122115#endif
    21132116
    2114     forEachNetworkSession([&callbackAggregator](auto& session) {
    2115         session.storageManager().suspend([callbackAggregator] { });
    2116     });
     2117    m_storageManagerSet->suspend([callbackAggregator] { });
    21172118}
    21182119
    … …  
    21902191#endif
    21912192
    2192     forEachNetworkSession([](auto& session) {
    2193         session.storageManager().resume();
    2194     });
     2193    m_storageManagerSet->resume();
    21952194}
    21962195
    … …  
    23972396#endif // ENABLE(INDEXED_DATABASE)
    23982397
     2398void NetworkProcess::syncLocalStorage(CompletionHandler<void()>&& completionHandler)
     2399{
     2400    m_storageManagerSet->waitUntilSyncingLocalStorageFinished();
     2401    completionHandler();
     2402}
     2403
     2404void NetworkProcess::clearLegacyPrivateBrowsingLocalStorage()
     2405{
     2406    if (m_storageManagerSet->contains(PAL::SessionID::legacyPrivateSessionID()))
     2407        m_storageManagerSet->deleteLocalStorageModifiedSince(PAL::SessionID::legacyPrivateSessionID(), -WallTime::infinity(), []() { });
     2408}
     2409
    23992410void NetworkProcess::updateQuotaBasedOnSpaceUsageForTesting(PAL::SessionID sessionID, const ClientOrigin& origin)
    24002411{
    … …  
    27042715}
    27052716
    2706 void NetworkProcess::webPageWasAdded(IPC::Connection& connection, PAL::SessionID sessionID, PageIdentifier pageID, PageIdentifier oldPageID)
    2707 {
    2708     if (!pageID || !oldPageID) {
    2709         LOG_ERROR("Cannot add page with invalid id");
    2710         return;
    2711     }
    2712 
    2713     auto* session = networkSession(sessionID);
    2714     if (!session) {
    2715         LOG_ERROR("Cannot add page to an unknown session");
    2716         return;
    2717     }
    2718     auto& storageManager = session->storageManager();
    2719 
    2720     auto addResult = m_sessionByConnection.add(connection.uniqueID(), sessionID);
    2721     ASSERT_UNUSED(addResult, addResult.iterator->value == sessionID);
    2722 
    2723     storageManager.createSessionStorageNamespace(pageID.toUInt64(), std::numeric_limits<unsigned>::max());
    2724     storageManager.addAllowedSessionStorageNamespaceConnection(pageID.toUInt64(), connection);
    2725     if (pageID != oldPageID)
    2726         storageManager.cloneSessionStorageNamespace(oldPageID.toUInt64(), pageID.toUInt64());
    2727 }
    2728 
    2729 void NetworkProcess::webPageWasRemoved(IPC::Connection& connection, PAL::SessionID sessionID, PageIdentifier pageID)
    2730 {
    2731     if (!pageID) {
    2732         LOG_ERROR("Cannot remove page with invalid id");
    2733         return;
    2734     }
    2735 
    2736     auto* session = networkSession(sessionID);
    2737     // Session can be destroyed before page gets removed.
    2738     if (!session)
    2739         return;
    2740 
    2741     auto& storageManager = session->storageManager();
    2742     storageManager.removeAllowedSessionStorageNamespaceConnection(pageID.toUInt64(), connection);
    2743     storageManager.destroySessionStorageNamespace(pageID.toUInt64());
    2744 }
    2745 
    2746 void NetworkProcess::webProcessWasDisconnected(IPC::Connection& connection)
    2747 {
    2748     auto sessionID = m_sessionByConnection.take(connection.uniqueID());
    2749     if (!sessionID.isValid())
    2750         return;
    2751 
    2752     if (auto* session = networkSession(sessionID))
    2753         session->storageManager().processDidCloseConnection(connection);
    2754 }
    2755 
    2756 void NetworkProcess::webProcessSessionChanged(IPC::Connection& connection, PAL::SessionID newSessionID, const Vector<PageIdentifier>& pageIDs)
    2757 {
    2758     auto connectionID = connection.uniqueID();
    2759     ASSERT(m_sessionByConnection.contains(connectionID));
    2760     if (m_sessionByConnection.get(connectionID) == newSessionID)
    2761         return;
    2762 
    2763     webProcessWasDisconnected(connection);
    2764     for (auto& pageID : pageIDs)
    2765         webPageWasAdded(connection, newSessionID, pageID, pageID);
    2766 }
    2767 
    27682717void NetworkProcess::getLocalStorageOriginDetails(PAL::SessionID sessionID, CompletionHandler<void(Vector<LocalStorageDatabaseTracker::OriginDetails>&&)>&& completionHandler)
    27692718{
    2770     auto* session = networkSession(sessionID);
    2771     if (!session) {
     2719    if (!m_storageManagerSet->contains(sessionID)) {
    27722720        LOG_ERROR("Cannot get local storage information for an unknown session");
    27732721        return;
    27742722    }
    27752723
    2776     auto& storageManager = session->storageManager();
    2777     storageManager.getLocalStorageOriginDetails([completionHandler = WTFMove(completionHandler)](auto&& details) mutable {
     2724    m_storageManagerSet->getLocalStorageOriginDetails(sessionID, [completionHandler = WTFMove(completionHandler)](auto&& details) mutable {
    27782725        completionHandler(WTFMove(details));
    27792726    });
    27802727}
    27812728
     2729void NetworkProcess::connectionToWebProcessClosed(IPC::Connection& connection)
     2730{
     2731    m_storageManagerSet->removeConnection(connection);
     2732}
     2733
    27822734} // namespace WebKit
  • trunk/Source/WebKit/NetworkProcess/NetworkProcess.h

    r248713 r248734  
    9898class NetworkProximityManager;
    9999class NetworkResourceLoader;
     100class StorageManagerSet;
    100101class WebSWServerConnection;
    101102class WebSWServerToContextConnection;
    … …  
    270271    bool sessionIsControlledByAutomation(PAL::SessionID) const;
    271272
    272     void webPageWasAdded(IPC::Connection&, PAL::SessionID, WebCore::PageIdentifier, WebCore::PageIdentifier);
    273     void webPageWasRemoved(IPC::Connection&, PAL::SessionID, WebCore::PageIdentifier);
    274     void webProcessWasDisconnected(IPC::Connection&);
    275     void webProcessSessionChanged(IPC::Connection&, PAL::SessionID, const Vector<WebCore::PageIdentifier>&);
     273    void connectionToWebProcessClosed(IPC::Connection&);
    276274    void getLocalStorageOriginDetails(PAL::SessionID, CompletionHandler<void(Vector<LocalStorageDatabaseTracker::OriginDetails>&&)>&&);
    277275
    … …  
    286284    void setIDBPerOriginQuota(uint64_t);
    287285#endif
     286
     287    void syncLocalStorage(CompletionHandler<void()>&&);
     288    void clearLegacyPrivateBrowsingLocalStorage();
     289
    288290    void updateQuotaBasedOnSpaceUsageForTesting(PAL::SessionID, const WebCore::ClientOrigin&);
    289291
    … …  
    500502    mutable std::unique_ptr<WebCore::NetworkStorageSession> m_defaultNetworkStorageSession;
    501503
     504    RefPtr<StorageManagerSet> m_storageManagerSet;
     505
    502506#if PLATFORM(COCOA)
    503507    void platformInitializeNetworkProcessCocoa(const NetworkProcessCreationParameters&);
  • trunk/Source/WebKit/NetworkProcess/NetworkProcess.messages.in

    r248699 r248734  
    164164    SetIDBPerOriginQuota(uint64_t quota)
    165165#endif
     166
     167    SyncLocalStorage() -> () Synchronous
     168    ClearLegacyPrivateBrowsingLocalStorage()
     169
    166170    UpdateQuotaBasedOnSpaceUsageForTesting(PAL::SessionID sessionID, struct WebCore::ClientOrigin origin)
    167171
  • trunk/Source/WebKit/NetworkProcess/NetworkSession.cpp

    r248144 r248734  
    3434#include "NetworkResourceLoader.h"
    3535#include "PingLoad.h"
    36 #include "StorageManager.h"
    3736#include "WebPageProxy.h"
    3837#include "WebPageProxyMessages.h"
    … …  
    8685#endif
    8786    , m_adClickAttribution(makeUniqueRef<AdClickAttributionManager>(parameters.sessionID))
    88     , m_storageManager(StorageManager::create(String(parameters.localStorageDirectory)))
    8987{
    9088    if (!m_sessionID.isEphemeral()) {
    … …  
    10098    }
    10199
    102     SandboxExtension::consumePermanently(parameters.localStorageDirectoryExtensionHandle);
    103100    m_adClickAttribution->setPingLoadFunction([this, weakThis = makeWeakPtr(this)](NetworkResourceLoadParameters&& loadParameters, CompletionHandler<void(const WebCore::ResourceError&, const WebCore::ResourceResponse&)>&& completionHandler) {
    104101        if (!weakThis)
    … …  
    114111    destroyResourceLoadStatistics();
    115112#endif
    116 
    117     m_storageManager->resume();
    118     m_storageManager->waitUntilTasksFinished();
    119113}
    120114
  • trunk/Source/WebKit/NetworkProcess/NetworkSession.h

    r248640 r248734  
    5353class NetworkProcess;
    5454class NetworkResourceLoader;
    55 class StorageManager;
    5655class NetworkSocketChannel;
    5756class WebResourceLoadStatisticsStore;
    … …  
    8180    void registerNetworkDataTask(NetworkDataTask& task) { m_dataTaskSet.add(&task); }
    8281    void unregisterNetworkDataTask(NetworkDataTask& task) { m_dataTaskSet.remove(&task); }
    83 
    84     StorageManager& storageManager() { return m_storageManager.get(); }
    8582
    8683#if ENABLE(RESOURCE_LOAD_STATISTICS)
    … …  
    146143    PrefetchCache m_prefetchCache;
    147144
    148     Ref<StorageManager> m_storageManager;
    149145#if !ASSERT_DISABLED
    150146    bool m_isInvalidated { false };
  • trunk/Source/WebKit/NetworkProcess/NetworkSessionCreationParameters.cpp

    r248668 r248734  
    5151        , { }, { }
    5252#endif
    53         , { }, { }, false, false, { }, { }, { }, { }, { }, { }, { }, { }, { }, { }
     53        , { }, { }, false, false, { }, { }, { }, { }, { }, { }, { }, { }
    5454    };
    5555}
    … …  
    8787    encoder << enableResourceLoadStatisticsNSURLSessionSwitching;
    8888
    89     encoder << localStorageDirectory << localStorageDirectoryExtensionHandle;
    9089    encoder << networkCacheDirectory << networkCacheDirectoryExtensionHandle;
    9190
    … …  
    214213    decoder >> enableResourceLoadStatisticsNSURLSessionSwitching;
    215214    if (!enableResourceLoadStatisticsNSURLSessionSwitching)
    216         return WTF::nullopt;
    217    
    218     Optional<String> localStorageDirectory;
    219     decoder >> localStorageDirectory;
    220     if (!localStorageDirectory)
    221         return WTF::nullopt;
    222 
    223     Optional<SandboxExtension::Handle> localStorageDirectoryExtensionHandle;
    224     decoder >> localStorageDirectoryExtensionHandle;
    225     if (!localStorageDirectoryExtensionHandle)
    226215        return WTF::nullopt;
    227216
    … …  
    278267        , WTFMove(*allLoadsBlockedByDeviceManagementRestrictionsForTesting)
    279268        , WTFMove(*resourceLoadStatisticsManualPrevalentResource)
    280         , WTFMove(*localStorageDirectory)
    281         , WTFMove(*localStorageDirectoryExtensionHandle)
    282269        , WTFMove(*networkCacheDirectory)
    283270        , WTFMove(*networkCacheDirectoryExtensionHandle)
  • trunk/Source/WebKit/NetworkProcess/NetworkSessionCreationParameters.h

    r248640 r248734  
    9393    WebCore::RegistrableDomain resourceLoadStatisticsManualPrevalentResource { };
    9494
    95     String localStorageDirectory;
    96     SandboxExtension::Handle localStorageDirectoryExtensionHandle;
    9795    String networkCacheDirectory;
    9896    SandboxExtension::Handle networkCacheDirectoryExtensionHandle;
  • trunk/Source/WebKit/NetworkProcess/WebStorage/LocalStorageDatabase.cpp

    r247486 r248734  
    260260        return;
    261261
    262     ASSERT(m_didScheduleDatabaseUpdate);
    263262    m_didScheduleDatabaseUpdate = false;
    264263
  • trunk/Source/WebKit/NetworkProcess/WebStorage/LocalStorageDatabase.h

    r245540 r248734  
    5656    void clear();
    5757
     58    void updateDatabase();
     59
    5860    // Will block until all pending changes have been written to disk.
    5961    void close();
    … …  
    7476
    7577    void scheduleDatabaseUpdate();
    76     void updateDatabase();
    7778    void updateDatabaseWithChangedItems(const HashMap<String, String>&);
    7879
  • trunk/Source/WebKit/NetworkProcess/WebStorage/LocalStorageDatabaseTracker.cpp

    r247250 r248734  
    4040using namespace WebCore;
    4141
    42 Ref<LocalStorageDatabaseTracker> LocalStorageDatabaseTracker::create(Ref<WorkQueue>&& queue, String&& localStorageDirectory)
     42Ref<LocalStorageDatabaseTracker> LocalStorageDatabaseTracker::create(String&& localStorageDirectory)
    4343{
    44     return adoptRef(*new LocalStorageDatabaseTracker(WTFMove(queue), WTFMove(localStorageDirectory)));
     44    return adoptRef(*new LocalStorageDatabaseTracker(WTFMove(localStorageDirectory)));
    4545}
    4646
    47 LocalStorageDatabaseTracker::LocalStorageDatabaseTracker(Ref<WorkQueue>&& queue, String&& localStorageDirectory)
    48     : m_queue(WTFMove(queue))
    49     , m_localStorageDirectory(WTFMove(localStorageDirectory))
     47LocalStorageDatabaseTracker::LocalStorageDatabaseTracker(String&& localStorageDirectory)
     48    : m_localStorageDirectory(WTFMove(localStorageDirectory))
    5049{
    51     ASSERT(RunLoop::isMain());
     50    ASSERT(!RunLoop::isMain());
    5251
    53     // Make sure the encoding is initialized before we start dispatching things to the queue.
    54     UTF8Encoding();
    55 
    56     m_queue->dispatch([protectedThis = makeRef(*this)]() mutable {
    57         // Delete legacy storageTracker database file.
    58         SQLiteFileSystem::deleteDatabaseFile(protectedThis->databasePath("StorageTracker.db"));
    59     });
     52    SQLiteFileSystem::deleteDatabaseFile(databasePath("StorageTracker.db"));
    6053}
    6154
    … …  
    6760LocalStorageDatabaseTracker::~LocalStorageDatabaseTracker()
    6861{
    69     ASSERT(RunLoop::isMain());
     62    ASSERT(!RunLoop::isMain());
    7063}
    7164
  • trunk/Source/WebKit/NetworkProcess/WebStorage/LocalStorageDatabaseTracker.h

    r247250 r248734  
    3636namespace WebKit {
    3737
    38 class LocalStorageDatabaseTracker : public ThreadSafeRefCounted<LocalStorageDatabaseTracker, WTF::DestructionThread::MainRunLoop> {
     38class LocalStorageDatabaseTracker : public ThreadSafeRefCounted<LocalStorageDatabaseTracker> {
    3939public:
    40     static Ref<LocalStorageDatabaseTracker> create(Ref<WorkQueue>&&, String&& localStorageDirectory);
     40    static Ref<LocalStorageDatabaseTracker> create(String&& localStorageDirectory);
    4141    ~LocalStorageDatabaseTracker();
    4242
    … …  
    6565
    6666private:
    67     LocalStorageDatabaseTracker(Ref<WorkQueue>&&, String&& localStorageDirectory);
     67    LocalStorageDatabaseTracker(String&& localStorageDirectory);
    6868
    6969    String databasePath(const String& filename) const;
    … …  
    7474        SkipIfNonExistent
    7575    };
    76 
    77     Ref<WorkQueue> m_queue;
    7876   
    7977    // It is not safe to use this member from a background thread, call localStorageDirectory() instead.
  • trunk/Source/WebKit/NetworkProcess/WebStorage/LocalStorageNamespace.cpp

    r248452 r248734  
    4848}
    4949
    50 auto LocalStorageNamespace::getOrCreateStorageArea(SecurityOriginData&& securityOrigin, IsEphemeral isEphemeral) -> Ref<StorageArea>
     50Ref<StorageArea> LocalStorageNamespace::getOrCreateStorageArea(SecurityOriginData&& securityOrigin, IsEphemeral isEphemeral)
    5151{
    5252    ASSERT(!RunLoop::isMain());
    … …  
    8282}
    8383
    84 void LocalStorageNamespace::cloneTo(LocalStorageNamespace& newLocalStorageNamespace)
    85 {
    86     ASSERT(!RunLoop::isMain());
    87     for (auto& pair : m_storageAreaMap)
    88         newLocalStorageNamespace.m_storageAreaMap.add(pair.key, pair.value->clone());
    89 }
    90 
    9184} // namespace WebKit
  • trunk/Source/WebKit/NetworkProcess/WebStorage/LocalStorageNamespace.h

    r248422 r248734  
    5555
    5656    Vector<WebCore::SecurityOriginData> ephemeralOrigins() const;
    57     void cloneTo(LocalStorageNamespace& newLocalStorageNamespace);
    5857
    5958private:
  • trunk/Source/WebKit/NetworkProcess/WebStorage/SessionStorageNamespace.cpp

    r248452 r248734  
    4444}
    4545
    46 void SessionStorageNamespace::addAllowedConnection(IPC::Connection::UniqueID allowedConnection)
    47 {
    48     ASSERT(!RunLoop::isMain());
    49     m_allowedConnections.add(allowedConnection);
    50 }
    51 
    52 
    53 void SessionStorageNamespace::removeAllowedConnection(IPC::Connection::UniqueID allowedConnection)
    54 {
    55     ASSERT(!RunLoop::isMain());
    56     ASSERT(m_allowedConnections.contains(allowedConnection));
    57     m_allowedConnections.remove(allowedConnection);
    58 }
    59 auto SessionStorageNamespace::getOrCreateStorageArea(SecurityOriginData&& securityOrigin) -> Ref<StorageArea>
     46Ref<StorageArea> SessionStorageNamespace::getOrCreateStorageArea(SecurityOriginData&& securityOrigin)
    6047{
    6148    ASSERT(!RunLoop::isMain());
  • trunk/Source/WebKit/NetworkProcess/WebStorage/SessionStorageNamespace.h

    r248422 r248734  
    4646    bool isEmpty() const { return m_storageAreaMap.isEmpty(); }
    4747
    48     const HashSet<IPC::Connection::UniqueID>& allowedConnections() const { return m_allowedConnections; }
    49     void addAllowedConnection(IPC::Connection::UniqueID);
    50     void removeAllowedConnection(IPC::Connection::UniqueID);
    51 
    5248    Ref<StorageArea> getOrCreateStorageArea(WebCore::SecurityOriginData&&);
    5349
    … …  
    6258    explicit SessionStorageNamespace(unsigned quotaInBytes);
    6359
    64     HashSet<IPC::Connection::UniqueID> m_allowedConnections;
    6560    unsigned m_quotaInBytes { 0 };
    6661
  • trunk/Source/WebKit/NetworkProcess/WebStorage/StorageArea.cpp

    r248542 r248734  
    3737using namespace WebCore;
    3838
     39static uint64_t generateStorageAreaIdentifier()
     40{
     41    static uint64_t identifier;
     42    return ++identifier;
     43}
     44
    3945StorageArea::StorageArea(LocalStorageNamespace* localStorageNamespace, const SecurityOriginData& securityOrigin, unsigned quotaInBytes)
    4046    : m_localStorageNamespace(makeWeakPtr(localStorageNamespace))
    … …  
    4248    , m_quotaInBytes(quotaInBytes)
    4349    , m_storageMap(StorageMap::create(m_quotaInBytes))
     50    , m_identifier(generateStorageAreaIdentifier())
    4451{
    4552    ASSERT(!RunLoop::isMain());
    … …  
    4956{
    5057    ASSERT(!RunLoop::isMain());
    51     ASSERT(m_eventListeners.isEmpty());
    5258
    5359    if (m_localStorageDatabase)
    … …  
    5561}
    5662
    57 void StorageArea::addListener(IPC::Connection::UniqueID connectionID, uint64_t storageMapID)
    58 {
    59     ASSERT(!RunLoop::isMain());
    60     ASSERT(!m_eventListeners.contains(std::make_pair(connectionID, storageMapID)));
    61     m_eventListeners.add(std::make_pair(connectionID, storageMapID));
    62 }
    63 
    64 void StorageArea::removeListener(IPC::Connection::UniqueID connectionID, uint64_t storageMapID)
    65 {
    66     ASSERT(!RunLoop::isMain());
    67     ASSERT(isEphemeral() || m_eventListeners.contains(std::make_pair(connectionID, storageMapID)));
    68     m_eventListeners.remove(std::make_pair(connectionID, storageMapID));
    69 }
    70 
    71 bool StorageArea::hasListener(IPC::Connection::UniqueID connectionID, uint64_t storageMapID) const
    72 {
    73     ASSERT(!RunLoop::isMain());
    74     return m_eventListeners.contains(std::make_pair(connectionID, storageMapID));
     63void StorageArea::addListener(IPC::Connection::UniqueID connectionID)
     64{
     65    ASSERT(!RunLoop::isMain());
     66    ASSERT(!m_eventListeners.contains(connectionID));
     67
     68    if (m_eventListeners.isEmpty() && !isEphemeral())
     69        openDatabaseAndImportItemsIfNeeded();
     70
     71    m_eventListeners.add(connectionID);
     72}
     73
     74void StorageArea::removeListener(IPC::Connection::UniqueID connectionID)
     75{
     76    ASSERT(!RunLoop::isMain());
     77    m_eventListeners.remove(connectionID);
     78}
     79
     80bool StorageArea::hasListener(IPC::Connection::UniqueID connectionID) const
     81{
     82    ASSERT(!RunLoop::isMain());
     83    return m_eventListeners.contains(connectionID);
    7584}
    7685
    … …  
    104113
    105114    dispatchEvents(sourceConnection, sourceStorageAreaID, key, oldValue, value, urlString);
    106 }
    107 
    108 void StorageArea::setItems(const HashMap<String, String>& items)
    109 {
    110     ASSERT(!RunLoop::isMain());
    111     // Import items from web process if items are not stored on disk.
    112     if (!isEphemeral())
    113         return;
    114 
    115     for (auto& item : items) {
    116         String oldValue;
    117         bool quotaException;
    118         auto newStorageMap = m_storageMap->setItem(item.key, item.value, oldValue, quotaException);
    119         if (newStorageMap)
    120             m_storageMap = WTFMove(newStorageMap);
    121        
    122         if (quotaException)
    123             return;
    124     }
    125115}
    126116
    … …  
    179169
    180170    for (auto it = m_eventListeners.begin(), end = m_eventListeners.end(); it != end; ++it) {
    181         RunLoop::main().dispatch([connectionID = it->first, destinationStorageAreaID = it->second] {
     171        RunLoop::main().dispatch([connectionID = *it, destinationStorageAreaID = m_identifier] {
    182172            if (auto* connection = IPC::Connection::connection(connectionID))
    183173                connection->send(Messages::StorageAreaMap::ClearCache(), destinationStorageAreaID);
    … …  
    193183
    194184    ASSERT(m_localStorageNamespace->storageManager()->localStorageDatabaseTracker());
     185    ASSERT(m_queue);
    195186    // We open the database here even if we've already imported our items to ensure that the database is open if we need to write to it.
    196187    if (!m_localStorageDatabase)
    197         m_localStorageDatabase = LocalStorageDatabase::create(m_localStorageNamespace->storageManager()->workQueue(), *m_localStorageNamespace->storageManager()->localStorageDatabaseTracker(), m_securityOrigin);
     188        m_localStorageDatabase = LocalStorageDatabase::create(*m_queue, *m_localStorageNamespace->storageManager()->localStorageDatabaseTracker(), m_securityOrigin);
    198189
    199190    if (m_didImportItemsFromDatabase)
    … …  
    208199    ASSERT(!RunLoop::isMain());
    209200    for (auto it = m_eventListeners.begin(), end = m_eventListeners.end(); it != end; ++it) {
    210         sourceStorageAreaID = it->first == sourceConnection ? sourceStorageAreaID : 0;
    211 
    212         RunLoop::main().dispatch([connectionID = it->first, sourceStorageAreaID, destinationStorageAreaID = it->second, key = key.isolatedCopy(), oldValue = oldValue.isolatedCopy(), newValue = newValue.isolatedCopy(), urlString = urlString.isolatedCopy()] {
     201        sourceStorageAreaID = *it == sourceConnection ? sourceStorageAreaID : 0;
     202
     203        RunLoop::main().dispatch([connectionID = *it, sourceStorageAreaID, destinationStorageAreaID = m_identifier, key = key.isolatedCopy(), oldValue = oldValue.isolatedCopy(), newValue = newValue.isolatedCopy(), urlString = urlString.isolatedCopy()] {
    213204            if (auto* connection = IPC::Connection::connection(connectionID))
    214205                connection->send(Messages::StorageAreaMap::DispatchStorageEvent(sourceStorageAreaID, key, oldValue, newValue, urlString), destinationStorageAreaID);
    … …  
    217208}
    218209
     210void StorageArea::syncToDatabase()
     211{
     212    if (!m_localStorageDatabase)
     213        return;
     214
     215    m_localStorageDatabase->updateDatabase();
     216}
     217
    219218} // namespace WebKit
  • trunk/Source/WebKit/NetworkProcess/WebStorage/StorageArea.h

    r248422 r248734  
    5050
    5151    const WebCore::SecurityOriginData& securityOrigin() const { return m_securityOrigin; }
     52    uint64_t identifier() { return m_identifier; }
    5253
    53     void addListener(IPC::Connection::UniqueID, uint64_t storageMapID);
    54     void removeListener(IPC::Connection::UniqueID, uint64_t storageMapID);
    55     bool hasListener(IPC::Connection::UniqueID, uint64_t storageMapID) const;
     54    void addListener(IPC::Connection::UniqueID);
     55    void removeListener(IPC::Connection::UniqueID);
     56    bool hasListener(IPC::Connection::UniqueID connectionID) const;
    5657
    5758    Ref<StorageArea> clone() const;
    5859
    5960    void setItem(IPC::Connection::UniqueID sourceConnection, uint64_t sourceStorageAreaID, const String& key, const String& value, const String& urlString, bool& quotaException);
    60     void setItems(const HashMap<String, String>&);
    6161    void removeItem(IPC::Connection::UniqueID sourceConnection, uint64_t sourceStorageAreaID, const String& key, const String& urlString);
    6262    void clear(IPC::Connection::UniqueID sourceConnection, uint64_t sourceStorageAreaID, const String& urlString);
    … …  
    6868
    6969    void openDatabaseAndImportItemsIfNeeded() const;
     70
     71    void setWorkQueue(RefPtr<WorkQueue>&& queue) { m_queue = WTFMove(queue); }
     72
     73    void syncToDatabase();
    7074
    7175private:
    … …  
    8387
    8488    RefPtr<WebCore::StorageMap> m_storageMap;
    85     HashSet<std::pair<IPC::Connection::UniqueID, uint64_t>> m_eventListeners;
     89    HashSet<IPC::Connection::UniqueID> m_eventListeners;
     90
     91    uint64_t m_identifier;
     92    RefPtr<WorkQueue> m_queue;
    8693};
    8794
  • trunk/Source/WebKit/NetworkProcess/WebStorage/StorageManager.cpp

    r248633 r248734  
    3333#include "StorageArea.h"
    3434#include "StorageAreaMapMessages.h"
    35 #include "StorageManagerMessages.h"
    3635#include "TransientLocalStorageNamespace.h"
    3736#include "WebProcessProxy.h"
    … …  
    4241#include <memory>
    4342#include <wtf/WorkQueue.h>
    44 #include <wtf/threads/BinarySemaphore.h>
    4543
    4644namespace WebKit {
    … …  
    5149
    5250StorageManager::StorageManager(String&& localStorageDirectory)
    53     : m_queue(WorkQueue::create("com.apple.WebKit.StorageManager"))
    54 {
    55     ASSERT(RunLoop::isMain());
    56 
    57     // Make sure the encoding is initialized before we start dispatching things to the queue.
    58     UTF8Encoding();
     51{
     52    ASSERT(!RunLoop::isMain());
     53
    5954    if (!localStorageDirectory.isNull())
    60         m_localStorageDatabaseTracker = LocalStorageDatabaseTracker::create(m_queue.copyRef(), WTFMove(localStorageDirectory));
     55        m_localStorageDatabaseTracker = LocalStorageDatabaseTracker::create(WTFMove(localStorageDirectory));
    6156}
    6257
    6358StorageManager::~StorageManager()
    6459{
    65     ASSERT(RunLoop::isMain());
     60    ASSERT(!RunLoop::isMain());
    6661}
    6762
    6863void StorageManager::createSessionStorageNamespace(uint64_t storageNamespaceID, unsigned quotaInBytes)
    6964{
    70     ASSERT(RunLoop::isMain());
    71     m_queue->dispatch([this, protectedThis = makeRef(*this), storageNamespaceID, quotaInBytes]() mutable {
    72         m_sessionStorageNamespaces.ensure(storageNamespaceID, [quotaInBytes] {
    73             return SessionStorageNamespace::create(quotaInBytes);
    74         });
     65    ASSERT(!RunLoop::isMain());
     66
     67    m_sessionStorageNamespaces.ensure(storageNamespaceID, [quotaInBytes] {
     68        return SessionStorageNamespace::create(quotaInBytes);
    7569    });
    7670}
    … …  
    7872void StorageManager::destroySessionStorageNamespace(uint64_t storageNamespaceID)
    7973{
    80     ASSERT(RunLoop::isMain());
    81     m_queue->dispatch([this, protectedThis = makeRef(*this), storageNamespaceID] {
    82         ASSERT(m_sessionStorageNamespaces.contains(storageNamespaceID));
    83         if (auto* sessionStorageNamespace = m_sessionStorageNamespaces.get(storageNamespaceID)) {
    84             if (sessionStorageNamespace->allowedConnections().isEmpty())
    85                 m_sessionStorageNamespaces.remove(storageNamespaceID);
    86         }
    87     });
    88 }
    89 
    90 void StorageManager::addAllowedSessionStorageNamespaceConnection(uint64_t storageNamespaceID, IPC::Connection& allowedConnection)
    91 {
    92     ASSERT(RunLoop::isMain());
    93     auto allowedConnectionID = allowedConnection.uniqueID();
    94     auto addResult = m_connections.add(allowedConnectionID);
    95     if (addResult.isNewEntry)
    96         allowedConnection.addWorkQueueMessageReceiver(Messages::StorageManager::messageReceiverName(), m_queue.get(), this);
    97 
    98     m_queue->dispatch([this, protectedThis = makeRef(*this), allowedConnectionID, storageNamespaceID]() mutable {
    99         ASSERT(m_sessionStorageNamespaces.contains(storageNamespaceID));
    100 
    101         m_sessionStorageNamespaces.get(storageNamespaceID)->addAllowedConnection(allowedConnectionID);
    102     });
    103 }
    104 
    105 void StorageManager::removeAllowedSessionStorageNamespaceConnection(uint64_t storageNamespaceID, IPC::Connection& allowedConnection)
    106 {
    107     ASSERT(RunLoop::isMain());
    108     auto allowedConnectionID = allowedConnection.uniqueID();
    109     m_queue->dispatch([this, protectedThis = makeRef(*this), allowedConnectionID, storageNamespaceID]() mutable {
    110         ASSERT(m_sessionStorageNamespaces.contains(storageNamespaceID));
    111         if (auto* sessionStorageNamespace = m_sessionStorageNamespaces.get(storageNamespaceID))
    112             sessionStorageNamespace->removeAllowedConnection(allowedConnectionID);
    113     });
     74    ASSERT(!RunLoop::isMain());
     75
     76    ASSERT(m_sessionStorageNamespaces.contains(storageNamespaceID));
     77    if (auto* sessionStorageNamespace = m_sessionStorageNamespaces.get(storageNamespaceID))
     78        m_sessionStorageNamespaces.remove(storageNamespaceID);
    11479}
    11580
    11681void StorageManager::cloneSessionStorageNamespace(uint64_t storageNamespaceID, uint64_t newStorageNamespaceID)
    11782{
    118     ASSERT(RunLoop::isMain());
    119     m_queue->dispatch([this, protectedThis = makeRef(*this), storageNamespaceID, newStorageNamespaceID] {
    120         SessionStorageNamespace* sessionStorageNamespace = m_sessionStorageNamespaces.get(storageNamespaceID);
    121         if (!sessionStorageNamespace) {
    122             // FIXME: We can get into this situation if someone closes the originating page from within a
    123             // createNewPage callback. We bail for now, but we should really find a way to keep the session storage alive
    124             // so we we'll clone the session storage correctly.
    125             return;
    126         }
    127 
    128         SessionStorageNamespace* newSessionStorageNamespace = m_sessionStorageNamespaces.get(newStorageNamespaceID);
    129         ASSERT(newSessionStorageNamespace);
    130 
    131         sessionStorageNamespace->cloneTo(*newSessionStorageNamespace);
    132 
    133         if (!m_localStorageDatabaseTracker) {
    134             if (auto* localStorageNamespace = m_localStorageNamespaces.get(storageNamespaceID)) {
    135                 LocalStorageNamespace* newlocalStorageNamespace = getOrCreateLocalStorageNamespace(newStorageNamespaceID);
    136                 localStorageNamespace->cloneTo(*newlocalStorageNamespace);
    137             }
    138         }
    139     });
    140 }
    141 
    142 void StorageManager::processDidCloseConnection(IPC::Connection& connection)
    143 {
    144     ASSERT(RunLoop::isMain());
    145     if (m_connections.remove(connection.uniqueID()))
    146         connection.removeWorkQueueMessageReceiver(Messages::StorageManager::messageReceiverName());
    147 
    148     m_queue->dispatch([this, protectedThis = makeRef(*this), connectionID = connection.uniqueID()]() mutable {
    149         Vector<std::pair<IPC::Connection::UniqueID, uint64_t>> connectionAndStorageMapIDPairsToRemove;
    150         for (auto& storageArea : m_storageAreasByConnection) {
    151             if (storageArea.key.first != connectionID)
    152                 continue;
    153            
    154             storageArea.value->removeListener(storageArea.key.first, storageArea.key.second);
    155             connectionAndStorageMapIDPairsToRemove.append(storageArea.key);
    156         }
    157        
    158         for (auto& pair : connectionAndStorageMapIDPairsToRemove)
    159             m_storageAreasByConnection.remove(pair);
    160 
    161         Vector<uint64_t> sessionStorageNameSpaceIDsToRemove;
    162         for (auto& sessionStorageNamespace : m_sessionStorageNamespaces) {
    163             if (sessionStorageNamespace.value->allowedConnections().contains(connectionID))
    164                 sessionStorageNamespace.value->removeAllowedConnection(connectionID);
    165            
    166             if (sessionStorageNamespace.value->allowedConnections().isEmpty())
    167                 sessionStorageNameSpaceIDsToRemove.append(sessionStorageNamespace.key);
    168         }
    169        
    170         for (auto id : sessionStorageNameSpaceIDsToRemove)
    171             m_sessionStorageNamespaces.remove(id);
    172     });
     83    ASSERT(!RunLoop::isMain());
     84
     85    SessionStorageNamespace* sessionStorageNamespace = m_sessionStorageNamespaces.get(storageNamespaceID);
     86    if (!sessionStorageNamespace)
     87        return;
     88
     89    SessionStorageNamespace* newSessionStorageNamespace = getOrCreateSessionStorageNamespace(newStorageNamespaceID);
     90    ASSERT(newSessionStorageNamespace);
     91
     92    sessionStorageNamespace->cloneTo(*newSessionStorageNamespace);
    17393}
    17494
    17595void StorageManager::getSessionStorageOrigins(Function<void(HashSet<WebCore::SecurityOriginData>&&)>&& completionHandler)
    17696{
    177     ASSERT(RunLoop::isMain());
    178     m_queue->dispatch([this, protectedThis = makeRef(*this), completionHandler = WTFMove(completionHandler)]() mutable {
    179         HashSet<SecurityOriginData> origins;
    180 
    181         for (const auto& sessionStorageNamespace : m_sessionStorageNamespaces.values()) {
    182             for (auto& origin : sessionStorageNamespace->origins())
    183                 origins.add(crossThreadCopy(origin));
    184         }
    185 
    186         RunLoop::main().dispatch([origins = WTFMove(origins), completionHandler = WTFMove(completionHandler)]() mutable {
    187             completionHandler(WTFMove(origins));
    188         });
     97    ASSERT(!RunLoop::isMain());
     98
     99    HashSet<SecurityOriginData> origins;
     100    for (const auto& sessionStorageNamespace : m_sessionStorageNamespaces.values()) {
     101        for (auto& origin : sessionStorageNamespace->origins())
     102        origins.add(crossThreadCopy(origin));
     103    }
     104
     105    RunLoop::main().dispatch([origins = WTFMove(origins), completionHandler = WTFMove(completionHandler)]() mutable {
     106        completionHandler(WTFMove(origins));
    189107    });
    190108}
    … …  
    192110void StorageManager::deleteSessionStorageOrigins(Function<void()>&& completionHandler)
    193111{
    194     ASSERT(RunLoop::isMain());
    195     m_queue->dispatch([this, protectedThis = makeRef(*this), completionHandler = WTFMove(completionHandler)]() mutable {
     112    ASSERT(!RunLoop::isMain());
     113
     114    for (auto& sessionStorageNamespace : m_sessionStorageNamespaces.values())
     115        sessionStorageNamespace->clearAllStorageAreas();
     116
     117    RunLoop::main().dispatch(WTFMove(completionHandler));
     118}
     119
     120void StorageManager::deleteSessionStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>& origins, Function<void()>&& completionHandler)
     121{
     122    ASSERT(!RunLoop::isMain());
     123
     124    for (auto& origin : origins) {
    196125        for (auto& sessionStorageNamespace : m_sessionStorageNamespaces.values())
    197             sessionStorageNamespace->clearAllStorageAreas();
    198 
    199         RunLoop::main().dispatch(WTFMove(completionHandler));
    200     });
    201 }
    202 
    203 void StorageManager::deleteSessionStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>& origins, Function<void()>&& completionHandler)
    204 {
    205     ASSERT(RunLoop::isMain());
    206     m_queue->dispatch([this, protectedThis = makeRef(*this), copiedOrigins = crossThreadCopy(origins), completionHandler = WTFMove(completionHandler)]() mutable {
    207         for (auto& origin : copiedOrigins) {
    208             for (auto& sessionStorageNamespace : m_sessionStorageNamespaces.values())
    209                 sessionStorageNamespace->clearStorageAreasMatchingOrigin(origin);
    210         }
    211 
    212         RunLoop::main().dispatch(WTFMove(completionHandler));
    213     });
     126            sessionStorageNamespace->clearStorageAreasMatchingOrigin(origin);
     127    }
     128
     129    RunLoop::main().dispatch(WTFMove(completionHandler));
    214130}
    215131
    216132void StorageManager::getLocalStorageOrigins(Function<void(HashSet<WebCore::SecurityOriginData>&&)>&& completionHandler)
    217133{
    218     ASSERT(RunLoop::isMain());
    219     m_queue->dispatch([this, protectedThis = makeRef(*this), completionHandler = WTFMove(completionHandler)]() mutable {
    220         HashSet<SecurityOriginData> origins;
    221 
    222         if (m_localStorageDatabaseTracker) {
    223             for (auto& origin : m_localStorageDatabaseTracker->origins())
    224                 origins.add(origin.isolatedCopy());
    225         } else {
    226             for (const auto& localStorageNameSpace : m_localStorageNamespaces.values()) {
    227                 for (auto& origin : localStorageNameSpace->ephemeralOrigins())
    228                     origins.add(origin.isolatedCopy());
    229             }
    230         }
    231 
    232         for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values()) {
    233             for (auto& origin : transientLocalStorageNamespace->origins())
     134    ASSERT(!RunLoop::isMain());
     135
     136    HashSet<SecurityOriginData> origins;
     137    if (m_localStorageDatabaseTracker) {
     138    for (auto& origin : m_localStorageDatabaseTracker->origins())
     139        origins.add(origin.isolatedCopy());
     140    } else {
     141        for (const auto& localStorageNameSpace : m_localStorageNamespaces.values()) {
     142            for (auto& origin : localStorageNameSpace->ephemeralOrigins())
    234143                origins.add(origin.isolatedCopy());
    235144        }
    236 
    237         RunLoop::main().dispatch([origins = WTFMove(origins), completionHandler = WTFMove(completionHandler)]() mutable {
    238             completionHandler(WTFMove(origins));
    239         });
     145    }
     146
     147    for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values()) {
     148        for (auto& origin : transientLocalStorageNamespace->origins())
     149            origins.add(origin.isolatedCopy());
     150    }
     151
     152    RunLoop::main().dispatch([origins = WTFMove(origins), completionHandler = WTFMove(completionHandler)]() mutable {
     153        completionHandler(WTFMove(origins));
    240154    });
    241155}
    … …  
    243157void StorageManager::getLocalStorageOriginDetails(Function<void(Vector<LocalStorageDatabaseTracker::OriginDetails>&&)>&& completionHandler)
    244158{
    245     ASSERT(RunLoop::isMain());
    246     m_queue->dispatch([this, protectedThis = makeRef(*this), completionHandler = WTFMove(completionHandler)]() mutable {
    247         Vector<LocalStorageDatabaseTracker::OriginDetails> originDetails;
    248         if (m_localStorageDatabaseTracker)
    249             originDetails = m_localStorageDatabaseTracker->originDetails().isolatedCopy();
    250 
    251         RunLoop::main().dispatch([originDetails = WTFMove(originDetails), completionHandler = WTFMove(completionHandler)]() mutable {
    252             completionHandler(WTFMove(originDetails));
    253         });
    254     });
    255 }
    256 
    257 void StorageManager::deleteLocalStorageEntriesForOrigin(const SecurityOriginData& securityOrigin)
    258 {
    259     ASSERT(RunLoop::isMain());
    260     m_queue->dispatch([this, protectedThis = makeRef(*this), copiedOrigin = securityOrigin.isolatedCopy()]() mutable {
    261         for (auto& localStorageNamespace : m_localStorageNamespaces.values())
    262             localStorageNamespace->clearStorageAreasMatchingOrigin(copiedOrigin);
     159    ASSERT(!RunLoop::isMain());
     160
     161    Vector<LocalStorageDatabaseTracker::OriginDetails> originDetails;
     162    if (m_localStorageDatabaseTracker)
     163        originDetails = crossThreadCopy(m_localStorageDatabaseTracker->originDetails());
     164
     165    RunLoop::main().dispatch([originDetails = WTFMove(originDetails), completionHandler = WTFMove(completionHandler)]() mutable {
     166        completionHandler(WTFMove(originDetails));
     167    });
     168}
     169
     170void StorageManager::deleteLocalStorageOriginsModifiedSince(WallTime time, Function<void()>&& completionHandler)
     171{
     172    ASSERT(!RunLoop::isMain());
     173
     174    if (m_localStorageDatabaseTracker) {
     175        auto originsToDelete = m_localStorageDatabaseTracker->databasesModifiedSince(time);
    263176
    264177        for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values())
    265             transientLocalStorageNamespace->clearStorageAreasMatchingOrigin(copiedOrigin);
    266 
    267         if (m_localStorageDatabaseTracker)
    268             m_localStorageDatabaseTracker->deleteDatabaseWithOrigin(copiedOrigin);
    269     });
    270 }
    271 
    272 void StorageManager::deleteLocalStorageOriginsModifiedSince(WallTime time, Function<void()>&& completionHandler)
    273 {
    274     ASSERT(RunLoop::isMain());
    275     m_queue->dispatch([this, protectedThis = makeRef(*this), time, completionHandler = WTFMove(completionHandler)]() mutable {
    276         if (m_localStorageDatabaseTracker) {
    277             auto originsToDelete = m_localStorageDatabaseTracker->databasesModifiedSince(time);
    278            
    279             for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values())
    280                 transientLocalStorageNamespace->clearAllStorageAreas();
    281 
    282             for (const auto& origin : originsToDelete) {
    283                 for (auto& localStorageNamespace : m_localStorageNamespaces.values())
    284                     localStorageNamespace->clearStorageAreasMatchingOrigin(origin);
    285                
    286                 m_localStorageDatabaseTracker->deleteDatabaseWithOrigin(origin);
    287             }
    288         } else {
    289             for (auto& localStorageNamespace : m_localStorageNamespaces.values())
    290                 localStorageNamespace->clearAllStorageAreas();
    291         }
    292 
    293         RunLoop::main().dispatch(WTFMove(completionHandler));
    294     });
    295 }
    296 
    297 void StorageManager::deleteLocalStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>& origins, Function<void()>&& completionHandler)
    298 {
    299     ASSERT(RunLoop::isMain());
    300     m_queue->dispatch([this, protectedThis = makeRef(*this), copiedOrigins = crossThreadCopy(origins), completionHandler = WTFMove(completionHandler)]() mutable {
    301         for (auto& origin : copiedOrigins) {
     178            transientLocalStorageNamespace->clearAllStorageAreas();
     179
     180        for (const auto& origin : originsToDelete) {
    302181            for (auto& localStorageNamespace : m_localStorageNamespaces.values())
    303182                localStorageNamespace->clearStorageAreasMatchingOrigin(origin);
    304 
    305             for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values())
    306                 transientLocalStorageNamespace->clearStorageAreasMatchingOrigin(origin);
    307 
    308             if (m_localStorageDatabaseTracker)
    309                 m_localStorageDatabaseTracker->deleteDatabaseWithOrigin(origin);
     183            m_localStorageDatabaseTracker->deleteDatabaseWithOrigin(origin);
    310184        }
    311 
    312         RunLoop::main().dispatch(WTFMove(completionHandler));
    313     });
    314 }
    315 
    316 void StorageManager::createLocalStorageMap(IPC::Connection& connection, uint64_t storageMapID, uint64_t storageNamespaceID, SecurityOriginData&& securityOriginData)
    317 {
    318     ASSERT(!RunLoop::isMain());
    319     auto connectionID = connection.uniqueID();
    320     std::pair<IPC::Connection::UniqueID, uint64_t> connectionAndStorageMapIDPair(connectionID, storageMapID);
    321 
    322     ASSERT((HashMap<std::pair<IPC::Connection::UniqueID, uint64_t>, RefPtr<StorageArea>>::isValidKey(connectionAndStorageMapIDPair)));
    323 
    324     auto result = m_storageAreasByConnection.add(connectionAndStorageMapIDPair, nullptr);
    325     ASSERT(result.isNewEntry);
    326     ASSERT((HashMap<uint64_t, RefPtr<LocalStorageNamespace>>::isValidKey(storageNamespaceID)));
    327 
    328     LocalStorageNamespace* localStorageNamespace = getOrCreateLocalStorageNamespace(storageNamespaceID);
    329     ASSERT(localStorageNamespace);
    330 
    331     auto storageArea = localStorageNamespace->getOrCreateStorageArea(WTFMove(securityOriginData), m_localStorageDatabaseTracker ? LocalStorageNamespace::IsEphemeral::No : LocalStorageNamespace::IsEphemeral::Yes);
    332     storageArea->addListener(connectionID, storageMapID);
    333 
    334     result.iterator->value = WTFMove(storageArea);
    335 }
    336 
    337 void StorageManager::createTransientLocalStorageMap(IPC::Connection& connection, uint64_t storageMapID, uint64_t storageNamespaceID, SecurityOriginData&& topLevelOriginData, SecurityOriginData&& origin)
    338 {
    339     ASSERT(!RunLoop::isMain());
    340     auto connectionID = connection.uniqueID();
    341 
    342     ASSERT(m_storageAreasByConnection.isValidKey({ connectionID, storageMapID }));
    343 
    344     // See if we already have session storage for this connection/origin combo.
    345     // If so, update the map with the new ID, otherwise keep on trucking.
    346     for (auto it = m_storageAreasByConnection.begin(), end = m_storageAreasByConnection.end(); it != end; ++it) {
    347         if (it->key.first != connectionID)
    348             continue;
    349         Ref<StorageArea> area = *it->value;
    350         if (!area->isEphemeral())
    351             continue;
    352         if (!origin.securityOrigin()->isSameSchemeHostPort(area->securityOrigin().securityOrigin().get()))
    353             continue;
    354         area->addListener(connectionID, storageMapID);
    355         // If the storageMapID used as key in m_storageAreasByConnection is no longer one of the StorageArea's listeners, then this means
    356         // that destroyStorageMap() was already called for that storageMapID but it decided not to remove it from m_storageAreasByConnection
    357         // so that we could reuse it later on for the same connection/origin combo. In this case, it is safe to remove the previous
    358         // storageMapID from m_storageAreasByConnection.
    359         if (!area->hasListener(connectionID, it->key.second))
    360             m_storageAreasByConnection.remove(it);
    361         m_storageAreasByConnection.add({ connectionID, storageMapID }, WTFMove(area));
    362         return;
    363     }
    364 
    365     auto& slot = m_storageAreasByConnection.add({ connectionID, storageMapID }, nullptr).iterator->value;
    366     ASSERT(!slot);
    367 
    368     auto* transientLocalStorageNamespace = getOrCreateTransientLocalStorageNamespace(storageNamespaceID, WTFMove(topLevelOriginData));
    369 
    370     auto storageArea = transientLocalStorageNamespace->getOrCreateStorageArea(WTFMove(origin));
    371     storageArea->addListener(connectionID, storageMapID);
    372 
    373     slot = WTFMove(storageArea);
    374 }
    375 
    376 void StorageManager::createSessionStorageMap(IPC::Connection& connection, uint64_t storageMapID, uint64_t storageNamespaceID, SecurityOriginData&& securityOriginData)
    377 {
    378     ASSERT(!RunLoop::isMain());
    379     auto connectionID = connection.uniqueID();
    380     ASSERT(m_sessionStorageNamespaces.isValidKey(storageNamespaceID));
    381 
    382     SessionStorageNamespace* sessionStorageNamespace = m_sessionStorageNamespaces.get(storageNamespaceID);
    383     if (!sessionStorageNamespace) {
    384         // We're getting an incoming message from the web process that's for session storage for a web page
    385         // that has already been closed, just ignore it.
    386         return;
    387     }
    388 
    389     ASSERT(m_storageAreasByConnection.isValidKey({ connectionID, storageMapID }));
    390 
    391     auto& slot = m_storageAreasByConnection.add({ connectionID, storageMapID }, nullptr).iterator->value;
    392     ASSERT(!slot);
    393     ASSERT(sessionStorageNamespace->allowedConnections().contains(connectionID));
    394 
    395     auto storageArea = sessionStorageNamespace->getOrCreateStorageArea(WTFMove(securityOriginData));
    396     storageArea->addListener(connectionID, storageMapID);
    397 
    398     slot = WTFMove(storageArea);
    399 }
    400 
    401 void StorageManager::destroyStorageMap(IPC::Connection& connection, uint64_t storageMapID)
    402 {
    403     ASSERT(!RunLoop::isMain());
    404     auto connectionID = connection.uniqueID();
    405 
    406     std::pair<IPC::Connection::UniqueID, uint64_t> connectionAndStorageMapIDPair(connectionID, storageMapID);
    407     ASSERT(m_storageAreasByConnection.isValidKey(connectionAndStorageMapIDPair));
    408 
    409     auto it = m_storageAreasByConnection.find(connectionAndStorageMapIDPair);
    410     if (it == m_storageAreasByConnection.end()) {
    411         // The connection has been removed because the last page was closed.
    412         return;
    413     }
    414 
    415     it->value->removeListener(connectionID, storageMapID);
    416 
    417     // Don't remove session storage maps. The web process may reconnect and expect the data to still be around.
    418     if (it->value->isEphemeral())
    419         return;
    420 
    421     m_storageAreasByConnection.remove(connectionAndStorageMapIDPair);
    422 }
    423 
    424 void StorageManager::prewarm(IPC::Connection& connection, uint64_t storageMapID)
    425 {
    426     ASSERT(!RunLoop::isMain());
    427     if (auto* storageArea = findStorageArea(connection, storageMapID))
    428         storageArea->openDatabaseAndImportItemsIfNeeded();
    429 }
    430 
    431 void StorageManager::getValues(IPC::Connection& connection, uint64_t storageMapID, uint64_t storageMapSeed, GetValuesCallback&& completionHandler)
    432 {
    433     ASSERT(!RunLoop::isMain());
    434     auto* storageArea = findStorageArea(connection, storageMapID);
    435 
    436     // This is a session storage area for a page that has already been closed. Ignore it.
    437     if (!storageArea)
    438         return completionHandler({ });
    439 
    440     completionHandler(storageArea->items());
    441     connection.send(Messages::StorageAreaMap::DidGetValues(storageMapSeed), storageMapID);
    442 }
    443 
    444 void StorageManager::setItem(IPC::Connection& connection, WebCore::SecurityOriginData&& securityOriginData, uint64_t storageMapID, uint64_t sourceStorageAreaID, uint64_t storageMapSeed, const String& key, const String& value, const String& urlString)
    445 {
    446     ASSERT(!RunLoop::isMain());
    447     auto* storageArea = findStorageArea(connection, storageMapID);
    448 
    449     // This is a session storage area for a page that has already been closed. Ignore it.
    450     if (!storageArea)
    451         return;
    452 
    453     bool quotaError;
    454     storageArea->setItem(connection.uniqueID(), sourceStorageAreaID, key, value, urlString, quotaError);
    455     connection.send(Messages::StorageAreaMap::DidSetItem(storageMapSeed, key, quotaError), storageMapID);
    456 }
    457 
    458 void StorageManager::setItems(IPC::Connection& connection, uint64_t storageMapID, const HashMap<String, String>& items)
    459 {
    460     ASSERT(!RunLoop::isMain());
    461     if (auto* storageArea = findStorageArea(connection, storageMapID))
    462         storageArea->setItems(items);
    463 }
    464 
    465 void StorageManager::removeItem(IPC::Connection& connection, WebCore::SecurityOriginData&& securityOriginData, uint64_t storageMapID, uint64_t sourceStorageAreaID, uint64_t storageMapSeed, const String& key, const String& urlString)
    466 {
    467     ASSERT(!RunLoop::isMain());
    468     auto* storageArea = findStorageArea(connection, storageMapID);
    469 
    470     // This is a session storage area for a page that has already been closed. Ignore it.
    471     if (!storageArea)
    472         return;
    473 
    474     storageArea->removeItem(connection.uniqueID(), sourceStorageAreaID, key, urlString);
    475     connection.send(Messages::StorageAreaMap::DidRemoveItem(storageMapSeed, key), storageMapID);
    476 }
    477 
    478 void StorageManager::clear(IPC::Connection& connection, WebCore::SecurityOriginData&& securityOriginData, uint64_t storageMapID, uint64_t sourceStorageAreaID, uint64_t storageMapSeed, const String& urlString)
    479 {
    480     ASSERT(!RunLoop::isMain());
    481     auto* storageArea = findStorageArea(connection, storageMapID);
    482 
    483     // This is a session storage area for a page that has already been closed. Ignore it.
    484     if (!storageArea)
    485         return;
    486 
    487     storageArea->clear(connection.uniqueID(), sourceStorageAreaID, urlString);
    488     connection.send(Messages::StorageAreaMap::DidClear(storageMapSeed), storageMapID);
    489 }
    490 
    491 void StorageManager::waitUntilTasksFinished()
    492 {
    493     ASSERT(RunLoop::isMain());
    494     BinarySemaphore semaphore;
    495     m_queue->dispatch([this, &semaphore] {
    496         Vector<std::pair<IPC::Connection::UniqueID, uint64_t>> connectionAndStorageMapIDPairsToRemove;
    497         for (auto& connectionStorageAreaPair : m_storageAreasByConnection) {
    498             connectionStorageAreaPair.value->removeListener(connectionStorageAreaPair.key.first, connectionStorageAreaPair.key.second);
    499             connectionAndStorageMapIDPairsToRemove.append(connectionStorageAreaPair.key);
    500         }
    501 
    502         for (auto& connectionStorageAreaPair : connectionAndStorageMapIDPairsToRemove)
    503             m_storageAreasByConnection.remove(connectionStorageAreaPair);
    504 
    505         m_sessionStorageNamespaces.clear();
    506         m_localStorageNamespaces.clear();
    507 
    508         semaphore.signal();
    509     });
    510     semaphore.wait();
    511 }
    512 
    513 void StorageManager::suspend(CompletionHandler<void()>&& completionHandler)
    514 {
    515     ASSERT(RunLoop::isMain());
    516     CompletionHandlerCallingScope completionHandlerCaller(WTFMove(completionHandler));
    517     if (!m_localStorageDatabaseTracker)
    518         return;
    519 
    520     Locker<Lock> stateLocker(m_stateLock);
    521     if (m_state != State::Running)
    522         return;
    523     m_state = State::WillSuspend;
    524 
    525     m_queue->dispatch([this, protectedThis = makeRef(*this), completionHandler = completionHandlerCaller.release()] () mutable {
    526         Locker<Lock> stateLocker(m_stateLock);
    527         ASSERT(m_state != State::Suspended);
    528 
    529         if (m_state != State::WillSuspend) {
    530             RunLoop::main().dispatch(WTFMove(completionHandler));
    531             return;
    532         }
    533 
    534         m_state = State::Suspended;
    535         RunLoop::main().dispatch(WTFMove(completionHandler));
    536        
    537         while (m_state == State::Suspended)
    538             m_stateChangeCondition.wait(m_stateLock);
    539         ASSERT(m_state == State::Running);
    540     });
    541 }
    542 
    543 void StorageManager::resume()
    544 {
    545     ASSERT(RunLoop::isMain());
    546     if (!m_localStorageDatabaseTracker)
    547         return;
    548 
    549     Locker<Lock> stateLocker(m_stateLock);
    550     auto previousState = m_state;
    551     m_state = State::Running;
    552     if (previousState == State::Suspended)
    553         m_stateChangeCondition.notifyOne();
    554 }
    555 
    556 StorageArea* StorageManager::findStorageArea(IPC::Connection& connection, uint64_t storageMapID) const
    557 {
    558     ASSERT(!RunLoop::isMain());
    559     std::pair<IPC::Connection::UniqueID, uint64_t> connectionAndStorageMapIDPair(connection.uniqueID(), storageMapID);
    560 
    561     if (!m_storageAreasByConnection.isValidKey(connectionAndStorageMapIDPair))
    562         return nullptr;
    563 
    564     return m_storageAreasByConnection.get(connectionAndStorageMapIDPair);
     185    } else {
     186        for (auto& localStorageNamespace : m_localStorageNamespaces.values())
     187            localStorageNamespace->clearAllStorageAreas();
     188    }
     189
     190    RunLoop::main().dispatch(WTFMove(completionHandler));
     191}
     192
     193void StorageManager::deleteLocalStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>& origins, Function<void()>&& completionHandler)
     194{
     195    ASSERT(!RunLoop::isMain());
     196
     197    for (auto& origin : origins) {
     198        for (auto& localStorageNamespace : m_localStorageNamespaces.values())
     199            localStorageNamespace->clearStorageAreasMatchingOrigin(origin);
     200
     201        for (auto& transientLocalStorageNamespace : m_transientLocalStorageNamespaces.values())
     202            transientLocalStorageNamespace->clearStorageAreasMatchingOrigin(origin);
     203
     204        if (m_localStorageDatabaseTracker)
     205            m_localStorageDatabaseTracker->deleteDatabaseWithOrigin(origin);
     206    }
     207
     208    RunLoop::main().dispatch(WTFMove(completionHandler));
     209}
     210
     211StorageArea* StorageManager::createLocalStorageArea(uint64_t storageNamespaceID, WebCore::SecurityOriginData&& origin)
     212{
     213    ASSERT(!RunLoop::isMain());
     214
     215    if (auto* localStorageNamespace = getOrCreateLocalStorageNamespace(storageNamespaceID))
     216        return localStorageNamespace->getOrCreateStorageArea(WTFMove(origin), m_localStorageDatabaseTracker ? LocalStorageNamespace::IsEphemeral::No : LocalStorageNamespace::IsEphemeral::Yes).ptr();
     217
     218    return nullptr;
     219}
     220
     221StorageArea* StorageManager::createTransientLocalStorageArea(uint64_t storageNamespaceID, WebCore::SecurityOriginData&& topLevelOrigin, WebCore::SecurityOriginData&& origin)
     222{
     223    ASSERT(!RunLoop::isMain());
     224    ASSERT((HashMap<uint64_t, RefPtr<TransientLocalStorageNamespace>>::isValidKey(storageNamespaceID)));
     225
     226    if (auto* transientLocalStorageNamespace = getOrCreateTransientLocalStorageNamespace(storageNamespaceID, WTFMove(topLevelOrigin)))
     227        return transientLocalStorageNamespace->getOrCreateStorageArea(WTFMove(origin)).ptr();
     228   
     229    return nullptr;
     230}
     231
     232StorageArea* StorageManager::createSessionStorageArea(uint64_t storageNamespaceID, WebCore::SecurityOriginData&& origin)
     233{
     234    ASSERT(!RunLoop::isMain());
     235    ASSERT((HashMap<uint64_t, RefPtr<SessionStorageNamespace>>::isValidKey(storageNamespaceID)));
     236
     237    if (auto* sessionStorageNamespace = getOrCreateSessionStorageNamespace(storageNamespaceID))
     238        return sessionStorageNamespace->getOrCreateStorageArea(WTFMove(origin)).ptr();
     239   
     240    return nullptr;
    565241}
    566242
    … …  
    568244{
    569245    ASSERT(!RunLoop::isMain());
     246
    570247    if (!m_localStorageNamespaces.isValidKey(storageNamespaceID))
    571248        return nullptr;
    … …  
    579256{
    580257    ASSERT(!RunLoop::isMain());
     258
    581259    if (!m_transientLocalStorageNamespaces.isValidKey({ storageNamespaceID, topLevelOrigin }))
    582260        return nullptr;
    583261
    584     return m_transientLocalStorageNamespaces.ensure({ storageNamespaceID, WTFMove(topLevelOrigin) }, [](){
     262    return m_transientLocalStorageNamespaces.ensure({ storageNamespaceID, WTFMove(topLevelOrigin) }, [] {
    585263        return TransientLocalStorageNamespace::create();
    586264    }).iterator->value.get();
    587265}
    588266
     267SessionStorageNamespace* StorageManager::getOrCreateSessionStorageNamespace(uint64_t storageNamespaceID)
     268{
     269    ASSERT(!RunLoop::isMain());
     270
     271    if (!m_sessionStorageNamespaces.isValidKey(storageNamespaceID))
     272        return nullptr;
     273
     274    return m_sessionStorageNamespaces.ensure(storageNamespaceID, [] {
     275        // We currently have no limit on session storage.
     276        return SessionStorageNamespace::create(std::numeric_limits<unsigned>::max());
     277    }).iterator->value.get();
     278}
     279
     280void StorageManager::clearStorageNamespaces()
     281{
     282    ASSERT(!RunLoop::isMain());
     283
     284    m_localStorageNamespaces.clear();
     285    m_transientLocalStorageNamespaces.clear();
     286    m_sessionStorageNamespaces.clear();
     287}
     288
    589289} // namespace WebKit
  • trunk/Source/WebKit/NetworkProcess/WebStorage/StorageManager.h

    r248422 r248734  
    5050using GetValuesCallback = CompletionHandler<void(const HashMap<String, String>&)>;
    5151
    52 class StorageManager : public IPC::Connection::WorkQueueMessageReceiver {
     52class StorageManager : public RefCounted<StorageManager> {
    5353public:
    5454    static Ref<StorageManager> create(String&& localStorageDirectory)
    … …  
    6161    void createSessionStorageNamespace(uint64_t storageNamespaceID, unsigned quotaInBytes);
    6262    void destroySessionStorageNamespace(uint64_t storageNamespaceID);
    63     void addAllowedSessionStorageNamespaceConnection(uint64_t storageNamespaceID, IPC::Connection&);
    64     void removeAllowedSessionStorageNamespaceConnection(uint64_t storageNamespaceID, IPC::Connection&);
    6563    void cloneSessionStorageNamespace(uint64_t storageNamespaceID, uint64_t newStorageNamespaceID);
    6664
    67     void processDidCloseConnection(IPC::Connection&);
    68     void waitUntilTasksFinished();
    69     void suspend(CompletionHandler<void()>&&);
    70     void resume();
     65    void getSessionStorageOrigins(Function<void(HashSet<WebCore::SecurityOriginData>&&)>&&);
     66    void deleteSessionStorageOrigins(Function<void()>&& completionHandler);
     67    void deleteSessionStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>&, Function<void()>&&);
    7168
    72     void getSessionStorageOrigins(Function<void(HashSet<WebCore::SecurityOriginData>&&)>&& completionHandler);
    73     void deleteSessionStorageOrigins(Function<void()>&& completionHandler);
    74     void deleteSessionStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>&, Function<void()>&& completionHandler);
     69    void getLocalStorageOrigins(Function<void(HashSet<WebCore::SecurityOriginData>&&)>&&);
     70    void deleteLocalStorageOriginsModifiedSince(WallTime, Function<void()>&&);
     71    void deleteLocalStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>&, Function<void()>&&);
     72    void getLocalStorageOriginDetails(Function<void(Vector<LocalStorageDatabaseTracker::OriginDetails>&&)>&&);
    7573
    76     void getLocalStorageOrigins(Function<void(HashSet<WebCore::SecurityOriginData>&&)>&& completionHandler);
    77     void deleteLocalStorageEntriesForOrigin(const WebCore::SecurityOriginData&);
    78 
    79     void deleteLocalStorageOriginsModifiedSince(WallTime, Function<void()>&& completionHandler);
    80     void deleteLocalStorageEntriesForOrigins(const Vector<WebCore::SecurityOriginData>&, Function<void()>&& completionHandler);
    81 
    82     void getLocalStorageOriginDetails(Function<void(Vector<LocalStorageDatabaseTracker::OriginDetails>&&)>&& completionHandler);
     74    void clearStorageNamespaces();
    8375
    8476    void didReceiveMessage(IPC::Connection&, IPC::Decoder&);
    … …  
    8779    LocalStorageDatabaseTracker* localStorageDatabaseTracker() const { return m_localStorageDatabaseTracker.get(); }
    8880   
    89     WorkQueue& workQueue() const { return m_queue.get(); }
    90    
    9181    static const unsigned localStorageDatabaseQuotaInBytes;
     82
     83    StorageArea* createLocalStorageArea(uint64_t storageNamespaceID, WebCore::SecurityOriginData&&);
     84    StorageArea* createTransientLocalStorageArea(uint64_t storageNamespaceID, WebCore::SecurityOriginData&&, WebCore::SecurityOriginData&&);
     85    StorageArea* createSessionStorageArea(uint64_t storageNamespaceID, WebCore::SecurityOriginData&&);
    9286
    9387private:
    9488    explicit StorageManager(String&& localStorageDirectory);
    9589
    96     // Message handlers.
    97     void createLocalStorageMap(IPC::Connection&, uint64_t storageMapID, uint64_t storageNamespaceID, WebCore::SecurityOriginData&&);
    98     void createTransientLocalStorageMap(IPC::Connection&, uint64_t storageMapID, uint64_t storageNamespaceID, WebCore::SecurityOriginData&& topLevelOriginData, WebCore::SecurityOriginData&&);
    99     void createSessionStorageMap(IPC::Connection&, uint64_t storageMapID, uint64_t storageNamespaceID, WebCore::SecurityOriginData&&);
    100     void destroyStorageMap(IPC::Connection&, uint64_t storageMapID);
    101 
    102     void getValues(IPC::Connection&, uint64_t storageMapID, uint64_t storageMapSeed, GetValuesCallback&&);
    103     void prewarm(IPC::Connection&, uint64_t storageMapID);
    104     void setItem(IPC::Connection&, WebCore::SecurityOriginData&&, uint64_t storageMapID, uint64_t sourceStorageAreaID, uint64_t storageMapSeed, const String& key, const String& value, const String& urlString);
    105     void setItems(IPC::Connection&, uint64_t storageMapID, const HashMap<String, String>& items);
    106     void removeItem(IPC::Connection&, WebCore::SecurityOriginData&&, uint64_t storageMapID, uint64_t sourceStorageAreaID, uint64_t storageMapSeed, const String& key, const String& urlString);
    107     void clear(IPC::Connection&, WebCore::SecurityOriginData&&, uint64_t storageMapID, uint64_t sourceStorageAreaID, uint64_t storageMapSeed, const String& urlString);
    108 
    109     StorageArea* findStorageArea(IPC::Connection&, uint64_t) const;
    110 
    11190    LocalStorageNamespace* getOrCreateLocalStorageNamespace(uint64_t storageNamespaceID);
    112 
    11391    TransientLocalStorageNamespace* getOrCreateTransientLocalStorageNamespace(uint64_t storageNamespaceID, WebCore::SecurityOriginData&& topLevelOrigin);
    114 
    115     Ref<WorkQueue> m_queue;
     92    SessionStorageNamespace* getOrCreateSessionStorageNamespace(uint64_t storageNamespaceID);
    11693
    11794    RefPtr<LocalStorageDatabaseTracker> m_localStorageDatabaseTracker;
    11895    HashMap<uint64_t, RefPtr<LocalStorageNamespace>> m_localStorageNamespaces;
    119 
    12096    HashMap<std::pair<uint64_t, WebCore::SecurityOriginData>, RefPtr<TransientLocalStorageNamespace>> m_transientLocalStorageNamespaces;
    121 
    12297    HashMap<uint64_t, RefPtr<SessionStorageNamespace>> m_sessionStorageNamespaces;
    123 
    124     HashMap<std::pair<IPC::Connection::UniqueID, uint64_t>, RefPtr<StorageArea>> m_storageAreasByConnection;
    125     HashSet<IPC::Connection::UniqueID> m_connections;
    126 
    127     enum class State {
    128         Running,
    129         WillSuspend,
    130         Suspended
    131     };
    132     State m_state { State::Running };
    133     Lock m_stateLock;
    134     Condition m_stateChangeCondition;
    13598};
    13699
  • trunk/Source/WebKit/Shared/WebsiteDataStoreParameters.cpp

    r243911 r248734  
    5353    encoder << serviceWorkerRegistrationDirectory << serviceWorkerRegistrationDirectoryExtensionHandle;
    5454#endif
     55
     56    encoder << localStorageDirectory << localStorageDirectoryExtensionHandle;
    5557
    5658    encoder << perOriginStorageQuota;
    … …  
    122124#endif
    123125
     126    Optional<String> localStorageDirectory;
     127    decoder >> localStorageDirectory;
     128    if (!localStorageDirectory)
     129        return WTF::nullopt;
     130    parameters.localStorageDirectory = WTFMove(*localStorageDirectory);
     131
     132    Optional<SandboxExtension::Handle> localStorageDirectoryExtensionHandle;
     133    decoder >> localStorageDirectoryExtensionHandle;
     134    if (!localStorageDirectoryExtensionHandle)
     135        return WTF::nullopt;
     136    parameters.localStorageDirectoryExtensionHandle = WTFMove(*localStorageDirectoryExtensionHandle);
     137
    124138    Optional<uint64_t> perOriginStorageQuota;
    125139    decoder >> perOriginStorageQuota;
    … …  
    150164        , { }, { }
    151165#endif
     166        , { }, { }
    152167    };
    153168}
  • trunk/Source/WebKit/Shared/WebsiteDataStoreParameters.h

    r243911 r248734  
    7171#endif
    7272
     73    String localStorageDirectory;
     74    SandboxExtension::Handle localStorageDirectoryExtensionHandle;
     75
    7376    uint64_t perOriginStorageQuota { WebCore::StorageQuotaManager::defaultQuota() };
    7477    uint64_t perThirdPartyOriginStorageQuota { WebCore::StorageQuotaManager::defaultThirdPartyQuota() };
  • trunk/Source/WebKit/Sources.txt

    r248631 r248734  
    7171NetworkProcess/WebStorage/StorageArea.cpp
    7272NetworkProcess/WebStorage/StorageManager.cpp
     73NetworkProcess/WebStorage/StorageManagerSet.cpp
    7374NetworkProcess/WebStorage/TransientLocalStorageNamespace.cpp
    7475
  • trunk/Source/WebKit/UIProcess/API/C/WKContext.cpp

    r248699 r248734  
    670670    WebKit::toImpl(contextRef)->clearCurrentModifierStateForTesting();
    671671}
     672
     673void WKContextSyncLocalStorage(WKContextRef contextRef, void* context, WKContextSyncLocalStorageCallback callback)
     674{
     675    WebKit::toImpl(contextRef)->syncLocalStorage([context, callback] {
     676        if (callback)
     677            callback(context);
     678    });
     679}
     680
     681void WKContextClearLegacyPrivateBrowsingLocalStorage(WKContextRef contextRef, void* context, WKContextClearLegacyPrivateBrowsingLocalStorageCallback callback)
     682{
     683    WebKit::toImpl(contextRef)->clearLegacyPrivateBrowsingLocalStorage([context, callback] {
     684        if (callback)
     685            callback(context);
     686    });
     687}
  • trunk/Source/WebKit/UIProcess/API/C/WKContextPrivate.h

    r248699 r248734  
    121121WK_EXPORT void WKContextClearCurrentModifierStateForTesting(WKContextRef context);
    122122
     123typedef void (*WKContextSyncLocalStorageCallback)(void* functionContext);
     124WK_EXPORT void WKContextSyncLocalStorage(WKContextRef contextRef, void* context, WKContextSyncLocalStorageCallback callback);
     125
     126typedef void (*WKContextClearLegacyPrivateBrowsingLocalStorageCallback)(void* functionContext);
     127WK_EXPORT void WKContextClearLegacyPrivateBrowsingLocalStorage(WKContextRef contextRef, void* context, WKContextClearLegacyPrivateBrowsingLocalStorageCallback callback);
     128
    123129#ifdef __cplusplus
    124130}
  • trunk/Source/WebKit/UIProcess/API/C/WKWebsiteDataStoreRef.cpp

    r248640 r248734  
    532532}
    533533
     534void WKWebsiteDataStoreRemoveLocalStorage(WKWebsiteDataStoreRef dataStoreRef, void* context, WKWebsiteDataStoreRemoveLocalStorageCallback callback)
     535{
     536    OptionSet<WebKit::WebsiteDataType> dataTypes = WebKit::WebsiteDataType::LocalStorage;
     537    WebKit::toImpl(dataStoreRef)->websiteDataStore().removeData(dataTypes, -WallTime::infinity(), [context, callback] {
     538        if (callback)
     539            callback(context);
     540    });
     541}
     542
    534543void WKWebsiteDataStoreRemoveAllServiceWorkerRegistrations(WKWebsiteDataStoreRef dataStoreRef, void* context, WKWebsiteDataStoreRemoveAllServiceWorkerRegistrationsCallback callback)
    535544{
  • trunk/Source/WebKit/UIProcess/API/C/WKWebsiteDataStoreRef.h

    r248640 r248734  
    122122WK_EXPORT void WKWebsiteDataStoreGetFetchCacheOrigins(WKWebsiteDataStoreRef dataStoreRef, void* context, WKWebsiteDataStoreGetFetchCacheOriginsFunction function);
    123123
     124typedef void (*WKWebsiteDataStoreRemoveLocalStorageCallback)(void* functionContext);
     125WK_EXPORT void WKWebsiteDataStoreRemoveLocalStorage(WKWebsiteDataStoreRef dataStoreRef, void* context, WKWebsiteDataStoreRemoveLocalStorageCallback callback);
     126
    124127typedef void (*WKWebsiteDataStoreGetFetchCacheSizeForOriginFunction)(uint64_t, void*);
    125128WK_EXPORT void WKWebsiteDataStoreGetFetchCacheSizeForOrigin(WKWebsiteDataStoreRef dataStoreRef, WKStringRef origin, void* context, WKWebsiteDataStoreGetFetchCacheSizeForOriginFunction function);
  • trunk/Source/WebKit/UIProcess/WebProcessPool.cpp

    r248699 r248734  
    584584    if (!localStorageDirectory)
    585585        localStorageDirectory = API::WebsiteDataStore::defaultLocalStorageDirectory();
    586     parameters.defaultDataStoreParameters.networkSessionParameters.localStorageDirectory = localStorageDirectory;
    587     SandboxExtension::createHandleForReadWriteDirectory(localStorageDirectory, parameters.defaultDataStoreParameters.networkSessionParameters.localStorageDirectoryExtensionHandle);
     586    parameters.defaultDataStoreParameters.localStorageDirectory = localStorageDirectory;
     587    SandboxExtension::createHandleForReadWriteDirectory(localStorageDirectory, parameters.defaultDataStoreParameters.localStorageDirectoryExtensionHandle);
    588588
    589589    if (m_websiteDataStore)
    … …  
    18081808    ensureNetworkProcess().send(Messages::NetworkProcess::SetIDBPerOriginQuota(quota), 0);
    18091809#endif
     1810}
     1811
     1812void WebProcessPool::syncLocalStorage(CompletionHandler<void()>&& completionHandler)
     1813{
     1814    sendSyncToNetworkingProcess(Messages::NetworkProcess::SyncLocalStorage(), Messages::NetworkProcess::SyncLocalStorage::Reply());
     1815    completionHandler();
     1816}
     1817
     1818void WebProcessPool::clearLegacyPrivateBrowsingLocalStorage(CompletionHandler<void()>&& completionHandler)
     1819{
     1820    if (m_networkProcess)
     1821        m_networkProcess->send(Messages::NetworkProcess::ClearLegacyPrivateBrowsingLocalStorage(), 0);
     1822    completionHandler();
    18101823}
    18111824
  • trunk/Source/WebKit/UIProcess/WebProcessPool.h

    r248699 r248734  
    318318
    319319    void syncNetworkProcessCookies();
     320    void syncLocalStorage(CompletionHandler<void()>&& callback);
     321    void clearLegacyPrivateBrowsingLocalStorage(CompletionHandler<void()>&& callback);
    320322
    321323    void setIDBPerOriginQuota(uint64_t);
  • trunk/Source/WebKit/UIProcess/WebsiteData/Cocoa/WebsiteDataStoreCocoa.mm

    r248640 r248734  
    110110        SandboxExtension::createHandleForReadWriteDirectory(resourceLoadStatisticsDirectory, resourceLoadStatisticsDirectoryHandle);
    111111
    112     auto localStorageDirectory = resolvedLocalStorageDirectory();
    113     SandboxExtension::Handle localStorageDirectoryExtensionHandle;
    114     if (!localStorageDirectory.isEmpty())
    115         SandboxExtension::createHandleForReadWriteDirectory(localStorageDirectory, localStorageDirectoryExtensionHandle);
    116 
    117112    auto networkCacheDirectory = resolvedNetworkCacheDirectory();
    118113    SandboxExtension::Handle networkCacheDirectoryExtensionHandle;
    … …  
    144139        m_configuration->allLoadsBlockedByDeviceManagementRestrictionsForTesting(),
    145140        WTFMove(resourceLoadStatisticsManualPrevalentResource),
    146         WTFMove(localStorageDirectory),
    147         WTFMove(localStorageDirectoryExtensionHandle),
    148141        WTFMove(networkCacheDirectory),
    149142        WTFMove(networkCacheDirectoryExtensionHandle),
    … …  
    181174#endif
    182175
     176    parameters.localStorageDirectory = resolvedLocalStorageDirectory();
     177    if (!parameters.localStorageDirectory.isEmpty())
     178        SandboxExtension::createHandleForReadWriteDirectory(parameters.localStorageDirectory, parameters.localStorageDirectoryExtensionHandle);
     179
    183180    parameters.perOriginStorageQuota = perOriginStorageQuota();
    184181    parameters.perThirdPartyOriginStorageQuota = perThirdPartyOriginStorageQuota();
  • trunk/Source/WebKit/UIProcess/WebsiteData/WebsiteDataStore.cpp

    r248640 r248734  
    19701970    auto localStorageDirectory = resolvedLocalStorageDirectory();
    19711971    if (!localStorageDirectory.isEmpty()) {
    1972         parameters.networkSessionParameters.localStorageDirectory = localStorageDirectory;
    1973         SandboxExtension::createHandleForReadWriteDirectory(localStorageDirectory, parameters.networkSessionParameters.localStorageDirectoryExtensionHandle);
     1972        parameters.localStorageDirectory = localStorageDirectory;
     1973        SandboxExtension::createHandleForReadWriteDirectory(localStorageDirectory, parameters.localStorageDirectoryExtensionHandle);
    19741974    }
    19751975
  • trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj

    r248631 r248734  
    294294                1AB1F7981D1B3613007C9BD1 /* WebPaymentCoordinatorProxyMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 1AB1F7941D1B3613007C9BD1 /* WebPaymentCoordinatorProxyMessageReceiver.cpp */; };
    295295                1AB1F7991D1B3613007C9BD1 /* WebPaymentCoordinatorProxyMessages.h in Headers */ = {isa = PBXBuildFile; fileRef = 1AB1F7951D1B3613007C9BD1 /* WebPaymentCoordinatorProxyMessages.h */; };
    296                 1AB31A9616BC688100F6DBC9 /* StorageManagerMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 1AB31A9416BC688100F6DBC9 /* StorageManagerMessageReceiver.cpp */; };
    297                 1AB31A9716BC688100F6DBC9 /* StorageManagerMessages.h in Headers */ = {isa = PBXBuildFile; fileRef = 1AB31A9516BC688100F6DBC9 /* StorageManagerMessages.h */; };
    298296                1AB40EE61BF677E300BA81BE /* WKMenuItemIdentifiersPrivate.h in Headers */ = {isa = PBXBuildFile; fileRef = 1AB40EE41BF677E300BA81BE /* WKMenuItemIdentifiersPrivate.h */; settings = {ATTRIBUTES = (Private, ); }; };
    299297                1AB474D8184D43FD0051B622 /* WKBundlePageLoaderClient.h in Headers */ = {isa = PBXBuildFile; fileRef = 1AB474D7184D43FD0051B622 /* WKBundlePageLoaderClient.h */; settings = {ATTRIBUTES = (Private, ); }; };
    … …  
    12761274                935EEB9B1277617C003322B8 /* WKBundleBackForwardListItem.h in Headers */ = {isa = PBXBuildFile; fileRef = 935EEB981277616D003322B8 /* WKBundleBackForwardListItem.h */; settings = {ATTRIBUTES = (Private, ); }; };
    12771275                935EEB9F127761AC003322B8 /* WKBundleBackForwardList.h in Headers */ = {isa = PBXBuildFile; fileRef = 935EEB961277616D003322B8 /* WKBundleBackForwardList.h */; settings = {ATTRIBUTES = (Private, ); }; };
     1276                9368EEDE2303A90200BDB11A /* StorageManagerSetMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9368EEDC2303A8D800BDB11A /* StorageManagerSetMessageReceiver.cpp */; };
     1277                9368EEDF2303A9ED00BDB11A /* StorageManagerSetMessages.h in Headers */ = {isa = PBXBuildFile; fileRef = 9368EEDD2303A8D800BDB11A /* StorageManagerSetMessages.h */; };
     1278                936B059823039097002FC06B /* StorageManagerSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 936B05952303900B002FC06B /* StorageManagerSet.h */; };
    12781279                93735EBB1C92986300336FA7 /* WKPreviewActionItemInternal.h in Headers */ = {isa = PBXBuildFile; fileRef = 93735EBA1C92986300336FA7 /* WKPreviewActionItemInternal.h */; };
    12791280                9391074F1BF6BC65008C17AD /* WKPreviewElementInfoInternal.h in Headers */ = {isa = PBXBuildFile; fileRef = 9391074E1BF6BC65008C17AD /* WKPreviewElementInfoInternal.h */; };
    … …  
    17081709                        filePatterns = "*.h";
    17091710                        fileType = pattern.proxy;
     1711                        inputFiles = (
     1712                        );
    17101713                        isEditable = 1;
    17111714                        outputFiles = (
    … …  
    23082311                1AB1F7941D1B3613007C9BD1 /* WebPaymentCoordinatorProxyMessageReceiver.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = WebPaymentCoordinatorProxyMessageReceiver.cpp; path = DerivedSources/WebKit2/WebPaymentCoordinatorProxyMessageReceiver.cpp; sourceTree = BUILT_PRODUCTS_DIR; };
    23092312                1AB1F7951D1B3613007C9BD1 /* WebPaymentCoordinatorProxyMessages.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = WebPaymentCoordinatorProxyMessages.h; path = DerivedSources/WebKit2/WebPaymentCoordinatorProxyMessages.h; sourceTree = BUILT_PRODUCTS_DIR; };
    2310                 1AB31A9416BC688100F6DBC9 /* StorageManagerMessageReceiver.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = StorageManagerMessageReceiver.cpp; path = DerivedSources/WebKit2/StorageManagerMessageReceiver.cpp; sourceTree = BUILT_PRODUCTS_DIR; };
    2311                 1AB31A9516BC688100F6DBC9 /* StorageManagerMessages.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = StorageManagerMessages.h; path = DerivedSources/WebKit2/StorageManagerMessages.h; sourceTree = BUILT_PRODUCTS_DIR; };
    23122313                1AB40EE31BF677E300BA81BE /* WKMenuItemIdentifiers.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = WKMenuItemIdentifiers.mm; sourceTree = "<group>"; };
    23132314                1AB40EE41BF677E300BA81BE /* WKMenuItemIdentifiersPrivate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKMenuItemIdentifiersPrivate.h; sourceTree = "<group>"; };
    … …  
    38983899                935EEB971277616D003322B8 /* WKBundleBackForwardListItem.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WKBundleBackForwardListItem.cpp; sourceTree = "<group>"; };
    38993900                935EEB981277616D003322B8 /* WKBundleBackForwardListItem.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKBundleBackForwardListItem.h; sourceTree = "<group>"; };
     3901                9368EEDC2303A8D800BDB11A /* StorageManagerSetMessageReceiver.cpp */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.cpp; fileEncoding = 4; name = StorageManagerSetMessageReceiver.cpp; path = DerivedSources/WebKit2/StorageManagerSetMessageReceiver.cpp; sourceTree = BUILT_PRODUCTS_DIR; };
     3902                9368EEDD2303A8D800BDB11A /* StorageManagerSetMessages.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = StorageManagerSetMessages.h; path = DerivedSources/WebKit2/StorageManagerSetMessages.h; sourceTree = BUILT_PRODUCTS_DIR; };
     3903                936B05952303900B002FC06B /* StorageManagerSet.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StorageManagerSet.h; sourceTree = "<group>"; };
     3904                936B05962303900B002FC06B /* StorageManagerSet.messages.in */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = StorageManagerSet.messages.in; sourceTree = "<group>"; };
     3905                936B05972303900B002FC06B /* StorageManagerSet.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StorageManagerSet.cpp; sourceTree = "<group>"; };
    39003906                93735EBA1C92986300336FA7 /* WKPreviewActionItemInternal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKPreviewActionItemInternal.h; sourceTree = "<group>"; };
    39013907                9391074E1BF6BC65008C17AD /* WKPreviewElementInfoInternal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKPreviewElementInfoInternal.h; sourceTree = "<group>"; };
    … …  
    39273933                93B26149227D147200B97A76 /* StorageManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StorageManager.h; sourceTree = "<group>"; };
    39283934                93B2614A227D147200B97A76 /* StorageManager.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StorageManager.cpp; sourceTree = "<group>"; };
    3929                 93B2614B227D147200B97A76 /* StorageManager.messages.in */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = StorageManager.messages.in; sourceTree = "<group>"; };
    39303935                93B2614C227D147200B97A76 /* LocalStorageDatabase.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LocalStorageDatabase.cpp; sourceTree = "<group>"; };
    39313936                93BA04DA2151ADF3007F455F /* WebSWServerConnection.messages.in */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = WebSWServerConnection.messages.in; sourceTree = "<group>"; };
    … …  
    73057310                                93B2614A227D147200B97A76 /* StorageManager.cpp */,
    73067311                                93B26149227D147200B97A76 /* StorageManager.h */,
    7307                                 93B2614B227D147200B97A76 /* StorageManager.messages.in */,
     7312                                936B05972303900B002FC06B /* StorageManagerSet.cpp */,
     7313                                936B05952303900B002FC06B /* StorageManagerSet.h */,
     7314                                936B05962303900B002FC06B /* StorageManagerSet.messages.in */,
    73087315                                46BEB6E222FBB21A00269867 /* TransientLocalStorageNamespace.cpp */,
    73097316                                46BEB6E122FBB21A00269867 /* TransientLocalStorageNamespace.h */,
    … …  
    87678774                                1A334DEB16DE8F88006A8E38 /* StorageAreaMapMessageReceiver.cpp */,
    87688775                                1A334DEC16DE8F88006A8E38 /* StorageAreaMapMessages.h */,
    8769                                 1AB31A9416BC688100F6DBC9 /* StorageManagerMessageReceiver.cpp */,
    8770                                 1AB31A9516BC688100F6DBC9 /* StorageManagerMessages.h */,
     8776                                9368EEDC2303A8D800BDB11A /* StorageManagerSetMessageReceiver.cpp */,
     8777                                9368EEDD2303A8D800BDB11A /* StorageManagerSetMessages.h */,
    87718778                                5118E9A51F295963003EF9F5 /* StorageProcessMessageReceiver.cpp */,
    87728779                                5118E9A61F295963003EF9F5 /* StorageProcessMessages.h */,
    … …  
    96719678                                1A334DEE16DE8F88006A8E38 /* StorageAreaMapMessages.h in Headers */,
    96729679                                93B2614D227D149E00B97A76 /* StorageManager.h in Headers */,
    9673                                 1AB31A9716BC688100F6DBC9 /* StorageManagerMessages.h in Headers */,
     9680                                936B059823039097002FC06B /* StorageManagerSet.h in Headers */,
     9681                                9368EEDF2303A9ED00BDB11A /* StorageManagerSetMessages.h in Headers */,
    96749682                                1AE00D6C18327C1200087DD7 /* StringReference.h in Headers */,
    96759683                                296BD85D15019BC30071F424 /* StringUtilities.h in Headers */,
    … …  
    1118511193                                2DE6943D18BD2A68005C15E5 /* SmartMagnificationControllerMessageReceiver.cpp in Sources */,
    1118611194                                1A334DED16DE8F88006A8E38 /* StorageAreaMapMessageReceiver.cpp in Sources */,
    11187                                 1AB31A9616BC688100F6DBC9 /* StorageManagerMessageReceiver.cpp in Sources */,
     11195                                9368EEDE2303A90200BDB11A /* StorageManagerSetMessageReceiver.cpp in Sources */,
    1118811196                                2D92A783212B6A7100F493FD /* StringReference.cpp in Sources */,
    1118911197                                2D11B7512126A282006F8878 /* UnifiedSource1-mm.mm in Sources */,
  • trunk/Source/WebKit/WebProcess/InjectedBundle/InjectedBundle.cpp

    r247283 r248734  
    4747#include "WebProcessMessages.h"
    4848#include "WebProcessPoolMessages.h"
     49#include "WebStorageNamespaceProvider.h"
    4950#include "WebUserContentController.h"
    5051#include "WebsiteDataStoreParameters.h"
    … …  
    349350{
    350351    ASSERT(!hasProcessPrivilege(ProcessPrivilege::CanAccessRawCookies));
    351     WebProcess::singleton().enablePrivateBrowsingForTesting(enabled);
     352    if (enabled)
     353        WebProcess::singleton().ensureLegacyPrivateBrowsingSessionInNetworkProcess();
    352354
    353355    PageGroup::pageGroup(pageGroup->identifier())->enableLegacyPrivateBrowsingForTesting(enabled);
     356
     357    auto webStorageNameSpaceProvider = WebStorageNamespaceProvider::getOrCreate(pageGroup->pageGroupID());
     358    webStorageNameSpaceProvider->enableLegacyPrivateBrowsingForTesting(enabled);
    354359}
    355360
  • trunk/Source/WebKit/WebProcess/WebProcess.cpp

    r248713 r248734  
    678678    // link) the WebPage gets created both in the synchronous handler and through the normal way.
    679679    auto result = m_pageMap.add(pageID, nullptr);
    680     auto oldPageID = parameters.oldPageID ? parameters.oldPageID.value() : pageID;
    681680    if (result.isNewEntry) {
    682681        ASSERT(!result.iterator->value);
    … …  
    689688        result.iterator->value->reinitializeWebPage(WTFMove(parameters));
    690689
    691     ensureNetworkProcessConnection().connection().send(Messages::NetworkConnectionToWebProcess::WebPageWasAdded(result.iterator->value->sessionID(), pageID, oldPageID), 0);
    692 
    693690    ASSERT(result.iterator->value);
    694691}
    … …  
    698695    ASSERT(m_pageMap.contains(pageID));
    699696
    700     ensureNetworkProcessConnection().connection().send(Messages::NetworkConnectionToWebProcess::WebPageWasRemoved(sessionID, pageID), 0);
    701697    pageWillLeaveWindow(pageID);
    702698    m_pageMap.remove(pageID);
    … …  
    12471243
    12481244        m_networkProcessConnection = NetworkProcessConnection::create(connectionIdentifier);
    1249 
    1250         // To recover web storage, network process needs to know active webpages to prepare session storage.
    1251         // FIXME: https://bugs.webkit.org/show_bug.cgi?id=198051.
    1252         // Webpage should be added when Storage is used, not when connection is re-established.
    1253         for (auto& page : m_pageMap) {
    1254             if (!page.value)
    1255                 continue;
    1256 
    1257             m_networkProcessConnection->connection().send(Messages::NetworkConnectionToWebProcess::WebPageWasAdded(page.value->sessionID(), page.key, page.key), 0);
    1258         }
    12591245    }
    12601246   
    … …  
    12871273    ASSERT_UNUSED(connection, m_networkProcessConnection == connection);
    12881274
    1289     for (auto* storageAreaMap : m_storageAreaMaps.values())
     1275    for (auto* storageAreaMap : copyToVector(m_storageAreaMaps.values()))
    12901276        storageAreaMap->disconnect();
    12911277
    … …  
    16881674StorageAreaMap* WebProcess::storageAreaMap(uint64_t identifier) const
    16891675{
    1690     ASSERT(m_storageAreaMaps.contains(identifier));
    16911676    return m_storageAreaMaps.get(identifier);
    1692 }
    1693 
    1694 void WebProcess::enablePrivateBrowsingForTesting(bool enable)
    1695 {
    1696     if (enable)
    1697         ensureLegacyPrivateBrowsingSessionInNetworkProcess();
    1698 
    1699     Vector<PageIdentifier> pageIDs;
    1700     for (auto& page : m_pageMap) {
    1701         if (page.value)
    1702             pageIDs.append(page.key);
    1703     }
    1704 
    1705     if (!pageIDs.isEmpty())
    1706         ensureNetworkProcessConnection().connection().send(Messages::NetworkConnectionToWebProcess::WebProcessSessionChanged(enable ? PAL::SessionID::legacyPrivateSessionID() : PAL::SessionID::defaultSessionID(), pageIDs), 0);
    17071677}
    17081678
  • trunk/Source/WebKit/WebProcess/WebProcess.h

    r248713 r248734  
    216216    StorageAreaMap* storageAreaMap(uint64_t identifier) const;
    217217
    218     void enablePrivateBrowsingForTesting(bool);
    219 
    220218#if PLATFORM(COCOA)
    221219    RetainPtr<CFDataRef> sourceApplicationAuditData() const;
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageAreaImpl.cpp

    r247555 r248734  
    3434#include <WebCore/SecurityOriginData.h>
    3535#include <WebCore/Settings.h>
     36#include <WebCore/StorageType.h>
    3637
    3738namespace WebKit {
    … …  
    5152StorageAreaImpl::StorageAreaImpl(Ref<StorageAreaMap>&& storageAreaMap)
    5253    : m_storageAreaID(generateStorageAreaID())
    53     , m_storageAreaMap(WTFMove(storageAreaMap))
     54    , m_storageAreaMap(makeWeakPtr(storageAreaMap.get()))
    5455{
    5556}
    … …  
    6162unsigned StorageAreaImpl::length()
    6263{
    63     return m_storageAreaMap->length();
     64    return m_storageAreaMap ? m_storageAreaMap->length() : 0;
    6465}
    6566
    6667String StorageAreaImpl::key(unsigned index)
    6768{
    68     return m_storageAreaMap->key(index);
     69    return m_storageAreaMap ? m_storageAreaMap->key(index) : nullString();
    6970}
    7071
    7172String StorageAreaImpl::item(const String& key)
    7273{
    73     return m_storageAreaMap->item(key);
    74 }
    75 
    76 bool StorageAreaImpl::prewarm()
    77 {
    78     return m_storageAreaMap->prewarm();
     74    return m_storageAreaMap ? m_storageAreaMap->item(key) : nullString();
    7975}
    8076
    … …  
    8379    ASSERT(!value.isNull());
    8480
    85     m_storageAreaMap->setItem(sourceFrame, this, key, value, quotaException);
     81    if (m_storageAreaMap)
     82        m_storageAreaMap->setItem(sourceFrame, this, key, value, quotaException);
    8683}
    8784
    8885void StorageAreaImpl::removeItem(Frame* sourceFrame, const String& key)
    8986{
    90     m_storageAreaMap->removeItem(sourceFrame, this, key);
     87    if (m_storageAreaMap)
     88        m_storageAreaMap->removeItem(sourceFrame, this, key);
    9189}
    9290
    9391void StorageAreaImpl::clear(Frame* sourceFrame)
    9492{
    95     m_storageAreaMap->clear(sourceFrame, this);
     93    if (m_storageAreaMap)
     94        m_storageAreaMap->clear(sourceFrame, this);
    9695}
    9796
    9897bool StorageAreaImpl::contains(const String& key)
    9998{
    100     return m_storageAreaMap->contains(key);
     99    if (m_storageAreaMap)
     100        return m_storageAreaMap->contains(key);
     101
     102    return false;
    101103}
    102104
    103105StorageType StorageAreaImpl::storageType() const
    104106{
    105     return m_storageAreaMap->storageType();
     107    if (m_storageAreaMap)
     108        return m_storageAreaMap->storageType();
     109
     110    // We probably need an Invalid type.
     111    return StorageType::Local;
    106112}
    107113
    … …  
    113119void StorageAreaImpl::incrementAccessCount()
    114120{
    115     // Storage access is handled in the UI process, so there's nothing to do here.
     121    // Storage access is handled in the network process, so there's nothing to do here.
    116122}
    117123
    118124void StorageAreaImpl::decrementAccessCount()
    119125{
    120     // Storage access is handled in the UI process, so there's nothing to do here.
     126    // Storage access is handled in the network process, so there's nothing to do here.
    121127}
    122128
    … …  
    127133}
    128134
    129 const SecurityOriginData& StorageAreaImpl::securityOrigin() const
    130 {
    131     return m_storageAreaMap->securityOrigin().data();
    132 }
    133 
    134135} // namespace WebKit
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageAreaImpl.h

    r247555 r248734  
    2929#include <WebCore/StorageArea.h>
    3030#include <wtf/HashMap.h>
     31#include <wtf/WeakPtr.h>
    3132
    3233namespace WebCore {
    … …  
    6162    void decrementAccessCount() override;
    6263    void closeDatabaseIfIdle() override;
    63     const WebCore::SecurityOriginData& securityOrigin() const override;
    64     bool prewarm() final;
    6564
    6665    uint64_t m_storageAreaID;
    67     Ref<StorageAreaMap> m_storageAreaMap;
     66    WeakPtr<StorageAreaMap> m_storageAreaMap;
    6867};
    6968
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageAreaMap.cpp

    r247555 r248734  
    3030#include "StorageAreaImpl.h"
    3131#include "StorageAreaMapMessages.h"
    32 #include "StorageManagerMessages.h"
     32#include "StorageManagerSetMessages.h"
    3333#include "StorageNamespaceImpl.h"
    3434#include "WebPage.h"
    … …  
    4949using namespace WebCore;
    5050
    51 static uint64_t generateStorageMapID()
    52 {
    53     static uint64_t storageMapID;
    54     return ++storageMapID;
    55 }
    56 
    5751Ref<StorageAreaMap> StorageAreaMap::create(StorageNamespaceImpl* storageNamespace, Ref<WebCore::SecurityOrigin>&& securityOrigin)
    5852{
    … …  
    6155
    6256StorageAreaMap::StorageAreaMap(StorageNamespaceImpl* storageNamespace, Ref<WebCore::SecurityOrigin>&& securityOrigin)
    63     : m_storageNamespace(*storageNamespace)
    64     , m_storageMapID(generateStorageMapID())
     57    : m_storageNamespace(storageNamespace)
     58    , m_storageMapID(0)
    6559    , m_storageType(storageNamespace->storageType())
    66     , m_storageNamespaceID(storageNamespace->storageNamespaceID())
    6760    , m_quotaInBytes(storageNamespace->quotaInBytes())
    6861    , m_securityOrigin(WTFMove(securityOrigin))
    6962    , m_currentSeed(0)
    7063    , m_hasPendingClear(false)
    71     , m_hasPendingGetValues(false)
    72 {
    73     WebProcess::singleton().registerStorageAreaMap(*this);
     64{
    7465    connect();
    7566}
    … …  
    7768StorageAreaMap::~StorageAreaMap()
    7869{
    79     if (m_storageType != StorageType::EphemeralLocal)
    80         WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::DestroyStorageMap(m_storageMapID), 0);
    81 
    82     m_storageNamespace->didDestroyStorageAreaMap(*this);
    83 
    84     WebProcess::singleton().unregisterStorageAreaMap(*this);
     70    disconnect();
    8571}
    8672
    … …  
    123109    m_pendingValueChanges.add(key);
    124110
    125     WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::SetItem(m_securityOrigin->data(), m_storageMapID, sourceArea->storageAreaID(), m_currentSeed, key, value, sourceFrame->document()->url()), 0);
     111    WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManagerSet::SetItem(m_storageMapID, sourceArea->storageAreaID(), m_currentSeed, key, value, sourceFrame->document()->url()), 0);
    126112}
    127113
    … …  
    139125    m_pendingValueChanges.add(key);
    140126
    141     WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::RemoveItem(m_securityOrigin->data(), m_storageMapID, sourceArea->storageAreaID(), m_currentSeed, key, sourceFrame->document()->url()), 0);
     127    WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManagerSet::RemoveItem(m_storageMapID, sourceArea->storageAreaID(), m_currentSeed, key, sourceFrame->document()->url()), 0);
    142128}
    143129
    144130void StorageAreaMap::clear(WebCore::Frame* sourceFrame, StorageAreaImpl* sourceArea)
    145131{
     132    connect();
     133
    146134    resetValues();
    147135
    148136    m_hasPendingClear = true;
    149137    m_storageMap = StorageMap::create(m_quotaInBytes);
    150     WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::Clear(m_securityOrigin->data(), m_storageMapID, sourceArea->storageAreaID(), m_currentSeed, sourceFrame->document()->url()), 0);
     138    WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManagerSet::Clear(m_storageMapID, sourceArea->storageAreaID(), m_currentSeed, sourceFrame->document()->url()), 0);
    151139}
    152140
    … …  
    164152    m_pendingValueChanges.clear();
    165153    m_hasPendingClear = false;
    166     m_hasPendingGetValues = false;
    167154    m_currentSeed++;
    168155}
    … …  
    179166    // (This flag does not yet exist). Since loadValuesIfNeeded() ends up being called from within JavaScript code, processing incoming synchronous messages
    180167    // could lead to weird reentrency bugs otherwise.
    181     WebProcess::singleton().ensureNetworkProcessConnection().connection().sendSync(Messages::StorageManager::GetValues(m_storageMapID, m_currentSeed), Messages::StorageManager::GetValues::Reply(values), 0);
     168    WebProcess::singleton().ensureNetworkProcessConnection().connection().sendSync(Messages::StorageManagerSet::GetValues(m_storageMapID), Messages::StorageManagerSet::GetValues::Reply(values), 0);
    182169
    183170    m_storageMap = StorageMap::create(m_quotaInBytes);
    184171    m_storageMap->importItems(WTFMove(values));
    185 
    186     // We want to ignore all changes until we get the DidGetValues message.
    187     m_hasPendingGetValues = true;
    188 }
    189 
    190 bool StorageAreaMap::prewarm()
    191 {
    192     if (m_didPrewarm || m_storageMap)
    193         return false;
    194     m_didPrewarm = true;
    195 
    196     connect();
    197     WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::Prewarm(m_storageMapID), 0);
    198     return true;
    199 }
    200 
    201 void StorageAreaMap::didGetValues(uint64_t storageMapSeed)
    202 {
    203     if (m_currentSeed != storageMapSeed)
    204         return;
    205 
    206     ASSERT(m_hasPendingGetValues);
    207     m_hasPendingGetValues = false;
    208172}
    209173
    … …  
    260224    ASSERT(!m_storageMap || m_storageMap->hasOneRef());
    261225
    262     // There's a clear pending or getValues pending we don't want to apply any changes until we get the corresponding DidClear/DidGetValues messages.
    263     if (m_hasPendingClear || m_hasPendingGetValues)
     226    // There is at least one clear pending we don't want to apply any changes until we get the corresponding DidClear messages.
     227    if (m_hasPendingClear)
    264228        return;
    265229
    … …  
    306270    }
    307271
    308     if (storageType() == StorageType::Session || storageType() == StorageType::EphemeralLocal)
     272    if (storageType() == StorageType::Session)
    309273        dispatchSessionStorageEvent(sourceStorageAreaID, key, oldValue, newValue, urlString);
    310274    else
    … …  
    319283void StorageAreaMap::dispatchSessionStorageEvent(uint64_t sourceStorageAreaID, const String& key, const String& oldValue, const String& newValue, const String& urlString)
    320284{
    321     // Namespace IDs for session storage namespaces and ephemeral local storage namespaces are equivalent to web page IDs
     285    // Namespace IDs for session storage namespaces are equivalent to web page IDs
    322286    // so we can get the right page here.
    323     WebPage* webPage = WebProcess::singleton().webPage(makeObjectIdentifier<PageIdentifierType>(m_storageNamespaceID));
     287    WebPage* webPage = WebProcess::singleton().webPage(makeObjectIdentifier<PageIdentifierType>(m_storageNamespace->storageNamespaceID()));
    324288    if (!webPage)
    325289        return;
    … …  
    355319    Vector<RefPtr<Frame>> frames;
    356320
    357     PageGroup& pageGroup = *WebProcess::singleton().webPageGroup(m_storageNamespaceID)->corePageGroup();
     321    // Namespace IDs for local storage namespaces are equivalent to web page group IDs.
     322    PageGroup& pageGroup = *WebProcess::singleton().webPageGroup(m_storageNamespace->storageNamespaceID())->corePageGroup();
    358323    const HashSet<Page*>& pages = pageGroup.pages();
    359324    for (HashSet<Page*>::const_iterator it = pages.begin(), end = pages.end(); it != end; ++it) {
    … …  
    382347void StorageAreaMap::connect()
    383348{
    384     if (!m_isDisconnected)
     349    if (m_storageMapID)
    385350        return;
    386351
    387352    switch (m_storageType) {
    388353    case StorageType::Local:
    389     case StorageType::EphemeralLocal:
    390354    case StorageType::TransientLocal:
    391355        if (SecurityOrigin* topLevelOrigin = m_storageNamespace->topLevelOrigin())
    392             WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::CreateTransientLocalStorageMap(m_storageMapID, m_storageNamespace->storageNamespaceID(), topLevelOrigin->data(), m_securityOrigin->data()), 0);
     356            WebProcess::singleton().ensureNetworkProcessConnection().connection().sendSync(Messages::StorageManagerSet::ConnectToTransientLocalStorageArea(m_storageNamespace->sessionID(), m_storageNamespace->storageNamespaceID(), topLevelOrigin->data(), m_securityOrigin->data()), Messages::StorageManagerSet::ConnectToTransientLocalStorageArea::Reply(m_storageMapID), 0);
    393357        else
    394             WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::CreateLocalStorageMap(m_storageMapID, m_storageNamespace->storageNamespaceID(), m_securityOrigin->data()), 0);
     358            WebProcess::singleton().ensureNetworkProcessConnection().connection().sendSync(Messages::StorageManagerSet::ConnectToLocalStorageArea(m_storageNamespace->sessionID(), m_storageNamespace->storageNamespaceID(), m_securityOrigin->data()), Messages::StorageManagerSet::ConnectToLocalStorageArea::Reply(m_storageMapID), 0);
    395359        break;
    396360    case StorageType::Session:
    397         WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::CreateSessionStorageMap(m_storageMapID, m_storageNamespace->storageNamespaceID(), m_securityOrigin->data()), 0);
    398     }
    399 
    400     if (m_storageMap)
    401         WebProcess::singleton().ensureNetworkProcessConnection().connection().send(Messages::StorageManager::SetItems(m_storageMapID, m_storageMap->items()), 0);
    402     m_isDisconnected = false;
     361        WebProcess::singleton().ensureNetworkProcessConnection().connection().sendSync(Messages::StorageManagerSet::ConnectToSessionStorageArea(m_storageNamespace->sessionID(), m_storageNamespace->storageNamespaceID(), m_securityOrigin->data()), Messages::StorageManagerSet::ConnectToSessionStorageArea::Reply(m_storageMapID), 0);
     362    }
     363
     364    if (m_storageMapID)
     365        WebProcess::singleton().registerStorageAreaMap(*this);
    403366}
    404367
    405368void StorageAreaMap::disconnect()
    406369{
    407     m_isDisconnected = true;
    408     if (m_storageType == StorageType::Session && m_storageMap) {
    409         m_pendingValueChanges.clear();
    410         m_hasPendingClear = false;
    411     } else
    412         resetValues();
     370    if (!m_storageMapID)
     371        return;
     372
     373    resetValues();
     374    WebProcess::singleton().unregisterStorageAreaMap(*this);
     375
     376    if (auto networkProcessConnection = WebProcess::singleton().existingNetworkProcessConnection())
     377        networkProcessConnection->connection().send(Messages::StorageManagerSet::DisconnectFromStorageArea(m_storageMapID), 0);
     378
     379    m_storageMapID = 0;
    413380}
    414381
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageAreaMap.h

    r247555 r248734  
    3333#include <wtf/RefCounted.h>
    3434#include <wtf/RefPtr.h>
     35#include <wtf/WeakPtr.h>
    3536
    3637namespace WebCore {
    … …  
    4445class StorageNamespaceImpl;
    4546
    46 class StorageAreaMap : public RefCounted<StorageAreaMap>, private IPC::MessageReceiver {
     47class StorageAreaMap : public RefCounted<StorageAreaMap>, private IPC::MessageReceiver, public CanMakeWeakPtr<StorageAreaMap> {
    4748public:
    4849    static Ref<StorageAreaMap> create(StorageNamespaceImpl*, Ref<WebCore::SecurityOrigin>&&);
    … …  
    5859    void clear(WebCore::Frame* sourceFrame, StorageAreaImpl* sourceArea);
    5960    bool contains(const String& key);
    60     bool prewarm();
    6161
    6262    // IPC::MessageReceiver
    … …  
    7272    StorageAreaMap(StorageNamespaceImpl*, Ref<WebCore::SecurityOrigin>&&);
    7373
    74     void didGetValues(uint64_t storageMapSeed);
    7574    void didSetItem(uint64_t storageMapSeed, const String& key, bool quotaError);
    7675    void didRemoveItem(uint64_t storageMapSeed, const String& key);
    … …  
    8988    void dispatchLocalStorageEvent(uint64_t sourceStorageAreaID, const String& key, const String& oldValue, const String& newValue, const String& urlString);
    9089
    91     Ref<StorageNamespaceImpl> m_storageNamespace;
     90    StorageNamespaceImpl* m_storageNamespace;
    9291
    9392    uint64_t m_storageMapID;
    9493
    9594    WebCore::StorageType m_storageType;
    96     uint64_t m_storageNamespaceID;
    9795    unsigned m_quotaInBytes;
    9896    Ref<WebCore::SecurityOrigin> m_securityOrigin;
    … …  
    102100    uint64_t m_currentSeed;
    103101    bool m_hasPendingClear;
    104     bool m_hasPendingGetValues;
    105102    HashCountedSet<String> m_pendingValueChanges;
    106 
    107     bool m_isDisconnected { true };
    108     bool m_didPrewarm { false };
    109103};
    110104
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageAreaMap.messages.in

    r219966 r248734  
    2222
    2323messages -> StorageAreaMap {
    24     DidGetValues(uint64_t storageMapSeed)
    2524    DidSetItem(uint64_t storageMapSeed, String key, bool quotaException)
    2625    DidRemoveItem(uint64_t storageMapSeed, String key)
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageNamespaceImpl.cpp

    r246079 r248734  
    2929#include "StorageAreaImpl.h"
    3030#include "StorageAreaMap.h"
     31#include "StorageManagerSetMessages.h"
    3132#include "WebPage.h"
    3233#include "WebPageGroupProxy.h"
    … …  
    4142using namespace WebCore;
    4243
    43 Ref<StorageNamespaceImpl> StorageNamespaceImpl::createSessionStorageNamespace(uint64_t identifier, unsigned quotaInBytes)
     44Ref<StorageNamespaceImpl> StorageNamespaceImpl::createSessionStorageNamespace(uint64_t identifier, unsigned quotaInBytes, PAL::SessionID sessionID)
    4445{
    45     return adoptRef(*new StorageNamespaceImpl(StorageType::Session, identifier, nullptr, quotaInBytes));
     46    return adoptRef(*new StorageNamespaceImpl(StorageType::Session, identifier, nullptr, quotaInBytes, sessionID));
    4647}
    4748
    48 Ref<StorageNamespaceImpl> StorageNamespaceImpl::createEphemeralLocalStorageNamespace(uint64_t identifier, unsigned quotaInBytes)
     49Ref<StorageNamespaceImpl> StorageNamespaceImpl::createLocalStorageNamespace(uint64_t identifier, unsigned quotaInBytes, PAL::SessionID sessionID)
    4950{
    50     return createLocalStorageNamespace(identifier, quotaInBytes, IsEphemeral::Yes);
     51    return adoptRef(*new StorageNamespaceImpl(StorageType::Local, identifier, nullptr, quotaInBytes, sessionID));
    5152}
    5253
    53 Ref<StorageNamespaceImpl> StorageNamespaceImpl::createLocalStorageNamespace(uint64_t identifier, unsigned quotaInBytes, IsEphemeral isEphemeral)
     54Ref<StorageNamespaceImpl> StorageNamespaceImpl::createTransientLocalStorageNamespace(uint64_t identifier, WebCore::SecurityOrigin& topLevelOrigin, uint64_t quotaInBytes, PAL::SessionID sessionID)
    5455{
    55     return adoptRef(*new StorageNamespaceImpl(isEphemeral == IsEphemeral::Yes ? StorageType::EphemeralLocal : StorageType::Local, identifier, nullptr, quotaInBytes));
     56    return adoptRef(*new StorageNamespaceImpl(StorageType::TransientLocal, identifier, &topLevelOrigin, quotaInBytes, sessionID));
    5657}
    5758
    58 Ref<StorageNamespaceImpl> StorageNamespaceImpl::createTransientLocalStorageNamespace(uint64_t identifier, WebCore::SecurityOrigin& topLevelOrigin, uint64_t quotaInBytes)
    59 {
    60     return adoptRef(*new StorageNamespaceImpl(StorageType::TransientLocal, identifier, &topLevelOrigin, quotaInBytes));
    61 }
    62 
    63 StorageNamespaceImpl::StorageNamespaceImpl(WebCore::StorageType storageType, uint64_t storageNamespaceID, WebCore::SecurityOrigin* topLevelOrigin, unsigned quotaInBytes)
     59StorageNamespaceImpl::StorageNamespaceImpl(WebCore::StorageType storageType, uint64_t storageNamespaceID, WebCore::SecurityOrigin* topLevelOrigin, unsigned quotaInBytes, PAL::SessionID sessionID)
    6460    : m_storageType(storageType)
    6561    , m_storageNamespaceID(storageNamespaceID)
    6662    , m_topLevelOrigin(topLevelOrigin)
    6763    , m_quotaInBytes(quotaInBytes)
     64    , m_sessionID(sessionID)
    6865{
    6966}
    … …  
    7875}
    7976
    80 Ref<StorageArea> StorageNamespaceImpl::storageArea(const SecurityOriginData& securityOrigin)
     77Ref<StorageArea> StorageNamespaceImpl::storageArea(const SecurityOriginData& securityOriginData)
    8178{
    8279    RefPtr<StorageAreaMap> map;
    8380
    84     auto& slot = m_storageAreaMaps.add(securityOrigin, nullptr).iterator->value;
     81    auto securityOrigin = securityOriginData.securityOrigin();
     82    auto& slot = m_storageAreaMaps.add(securityOrigin->data(), nullptr).iterator->value;
    8583    if (!slot) {
    86         map = StorageAreaMap::create(this, securityOrigin.securityOrigin());
     84        map = StorageAreaMap::create(this, WTFMove(securityOrigin));
    8785        slot = map.get();
    8886    } else
    … …  
    9694    ASSERT(m_storageNamespaceID);
    9795
    98     if (m_storageType == StorageType::Session)
    99         return createSessionStorageNamespace(WebPage::fromCorePage(newPage)->pageID().toUInt64(), m_quotaInBytes);
     96    if (auto networkProcessConnection = WebProcess::singleton().existingNetworkProcessConnection())
     97        networkProcessConnection->connection().send(Messages::StorageManagerSet::CloneSessionStorageNamespace(newPage->sessionID(), m_storageNamespaceID, WebPage::fromCorePage(newPage)->pageID().toUInt64()), 0);
    10098
    101     ASSERT(m_storageType == StorageType::EphemeralLocal);
    102     auto newNamespace = adoptRef(*new StorageNamespaceImpl(m_storageType, m_storageNamespaceID, m_topLevelOrigin.get(), m_quotaInBytes));
     99    return adoptRef(*new StorageNamespaceImpl(m_storageType, WebPage::fromCorePage(newPage)->pageID().toUInt64(), m_topLevelOrigin.get(), m_quotaInBytes, newPage->sessionID()));
     100}
    103101
    104     return newNamespace;
     102void StorageNamespaceImpl::setSessionIDForTesting(PAL::SessionID sessionID)
     103{
     104    m_sessionID = sessionID;
     105    for (auto storageAreaMap : m_storageAreaMaps.values())
     106        storageAreaMap->disconnect();
    105107}
    106108
  • trunk/Source/WebKit/WebProcess/WebStorage/StorageNamespaceImpl.h

    r246079 r248734  
    4040class StorageNamespaceImpl : public WebCore::StorageNamespace {
    4141public:
    42     static Ref<StorageNamespaceImpl> createSessionStorageNamespace(uint64_t identifier, unsigned quotaInBytes);
    43     static Ref<StorageNamespaceImpl> createEphemeralLocalStorageNamespace(uint64_t identifier, unsigned quotaInBytes);
    44 
    45     enum class IsEphemeral : bool { No, Yes };
    46     static Ref<StorageNamespaceImpl> createLocalStorageNamespace(uint64_t identifier, unsigned quotaInBytes, IsEphemeral isEphemeral);
    47     static Ref<StorageNamespaceImpl> createTransientLocalStorageNamespace(uint64_t identifier, WebCore::SecurityOrigin& topLevelOrigin, uint64_t quotaInBytes);
     42    static Ref<StorageNamespaceImpl> createSessionStorageNamespace(uint64_t identifier, unsigned quotaInBytes, PAL::SessionID);
     43    static Ref<StorageNamespaceImpl> createLocalStorageNamespace(uint64_t identifier, unsigned quotaInBytes, PAL::SessionID);
     44    static Ref<StorageNamespaceImpl> createTransientLocalStorageNamespace(uint64_t identifier, WebCore::SecurityOrigin& topLevelOrigin, uint64_t quotaInBytes, PAL::SessionID);
    4845
    4946    virtual ~StorageNamespaceImpl();
    … …  
    5350    WebCore::SecurityOrigin* topLevelOrigin() const { return m_topLevelOrigin.get(); }
    5451    unsigned quotaInBytes() const { return m_quotaInBytes; }
     52    PAL::SessionID sessionID() const override { return m_sessionID; }
    5553
    5654    void didDestroyStorageAreaMap(StorageAreaMap&);
    5755
     56    void setSessionIDForTesting(PAL::SessionID) override;
     57
    5858private:
    59     explicit StorageNamespaceImpl(WebCore::StorageType, uint64_t storageNamespaceID, WebCore::SecurityOrigin* topLevelOrigin, unsigned quotaInBytes);
     59    explicit StorageNamespaceImpl(WebCore::StorageType, uint64_t storageNamespaceID, WebCore::SecurityOrigin* topLevelOrigin, unsigned quotaInBytes, PAL::SessionID);
    6060
    6161    Ref<WebCore::StorageArea> storageArea(const WebCore::SecurityOriginData&) override;
    … …  
    7070    const unsigned m_quotaInBytes;
    7171
    72     HashMap<WebCore::SecurityOriginData, StorageAreaMap*> m_storageAreaMaps;
     72    PAL::SessionID m_sessionID;
     73
     74    HashMap<WebCore::SecurityOriginData, RefPtr<StorageAreaMap>> m_storageAreaMaps;
    7375};
    7476
  • trunk/Source/WebKit/WebProcess/WebStorage/WebStorageNamespaceProvider.cpp

    r246079 r248734  
    6868Ref<WebCore::StorageNamespace> WebStorageNamespaceProvider::createSessionStorageNamespace(Page& page, unsigned quota)
    6969{
    70     return StorageNamespaceImpl::createSessionStorageNamespace(WebPage::fromCorePage(&page)->pageID().toUInt64(), quota);
     70    return StorageNamespaceImpl::createSessionStorageNamespace(WebPage::fromCorePage(&page)->pageID().toUInt64(), quota, page.sessionID());
    7171}
    7272
    73 Ref<WebCore::StorageNamespace> WebStorageNamespaceProvider::createEphemeralLocalStorageNamespace(Page& page, unsigned quota)
     73Ref<WebCore::StorageNamespace> WebStorageNamespaceProvider::createLocalStorageNamespace(unsigned quota, PAL::SessionID sessionID)
    7474{
    75     return StorageNamespaceImpl::createEphemeralLocalStorageNamespace(WebPage::fromCorePage(&page)->pageID().toUInt64(), quota);
     75    return StorageNamespaceImpl::createLocalStorageNamespace(m_identifier, quota, sessionID);
    7676}
    7777
    78 Ref<WebCore::StorageNamespace> WebStorageNamespaceProvider::createLocalStorageNamespace(unsigned quota)
     78Ref<WebCore::StorageNamespace> WebStorageNamespaceProvider::createTransientLocalStorageNamespace(WebCore::SecurityOrigin& topLevelOrigin, unsigned quota, PAL::SessionID sessionID)
    7979{
    80     return StorageNamespaceImpl::createLocalStorageNamespace(m_identifier, quota, StorageNamespaceImpl::IsEphemeral::No);
    81 }
    82 
    83 Ref<WebCore::StorageNamespace> WebStorageNamespaceProvider::createTransientLocalStorageNamespace(WebCore::SecurityOrigin& topLevelOrigin, unsigned quota)
    84 {
    85     return StorageNamespaceImpl::createTransientLocalStorageNamespace(m_identifier, topLevelOrigin, quota);
     80    return StorageNamespaceImpl::createTransientLocalStorageNamespace(m_identifier, topLevelOrigin, quota, sessionID);
    8681}
    8782
  • trunk/Source/WebKit/WebProcess/WebStorage/WebStorageNamespaceProvider.h

    r239535 r248734  
    3939
    4040    Ref<WebCore::StorageNamespace> createSessionStorageNamespace(WebCore::Page&, unsigned quota) override;
    41     Ref<WebCore::StorageNamespace> createEphemeralLocalStorageNamespace(WebCore::Page&, unsigned quota) override;
    42     Ref<WebCore::StorageNamespace> createLocalStorageNamespace(unsigned quota) override;
    43     Ref<WebCore::StorageNamespace> createTransientLocalStorageNamespace(WebCore::SecurityOrigin&, unsigned quota) override;
     41    Ref<WebCore::StorageNamespace> createLocalStorageNamespace(unsigned quota, PAL::SessionID) override;
     42    Ref<WebCore::StorageNamespace> createTransientLocalStorageNamespace(WebCore::SecurityOrigin&, unsigned quota, PAL::SessionID) override;
    4443
    4544    const uint64_t m_identifier;
  • trunk/Source/WebKitLegacy/ChangeLog

    r248699 r248734  
     12019-08-15  Sihui Liu  <sihui_liu@apple.com>
     2
     3        Some improvements on web storage
     4        https://bugs.webkit.org/show_bug.cgi?id=200373
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        Do some clean-up and add support for session change of web storage in layout tests.
     9
     10        * Storage/StorageAreaImpl.cpp:
     11        (WebKit::StorageAreaImpl::sessionChanged):
     12        * Storage/StorageAreaImpl.h:
     13        (): Deleted.
     14
     15        * Storage/StorageAreaSync.h: make sure StorageAreaSync is destructed on the main thread, as it can be
     16        dereferenced in StorageAreaImpl::sessionChanged and its last reference for final sync could be released on the
     17        background thread.
     18
     19        * Storage/StorageNamespaceImpl.cpp: replace EphemeralLocalStorage with LocalStorage, and store SessionID in
     20        StorageNamespace.
     21        (WebKit::StorageNamespaceImpl::createSessionStorageNamespace):
     22        (WebKit::StorageNamespaceImpl::getOrCreateLocalStorageNamespace):
     23        (WebKit::StorageNamespaceImpl::StorageNamespaceImpl):
     24        (WebKit::StorageNamespaceImpl::copy):
     25        (WebKit::StorageNamespaceImpl::close):
     26        (WebKit::StorageNamespaceImpl::setSessionIDForTesting):
     27        (WebKit::StorageNamespaceImpl::createEphemeralLocalStorageNamespace): Deleted.
     28        * Storage/StorageNamespaceImpl.h:
     29        * Storage/WebStorageNamespaceProvider.cpp:
     30        (WebKit::WebStorageNamespaceProvider::createSessionStorageNamespace):
     31        (WebKit::WebStorageNamespaceProvider::createLocalStorageNamespace):
     32        (WebKit::WebStorageNamespaceProvider::createTransientLocalStorageNamespace):
     33        (WebKit::WebStorageNamespaceProvider::createEphemeralLocalStorageNamespace): Deleted.
     34        * Storage/WebStorageNamespaceProvider.h:
     35
    1362019-08-14  Ryan Haddad  <ryanhaddad@apple.com>
    237
  • trunk/Source/WebKitLegacy/Storage/StorageAreaImpl.cpp

    r247486 r248734  
    293293}
    294294
     295void StorageAreaImpl::sessionChanged(bool isNewSessionPersistent)
     296{
     297    ASSERT(isMainThread());
     298
     299    unsigned quota = m_storageMap->quota();
     300    m_storageMap = StorageMap::create(quota);
     301
     302    if (isNewSessionPersistent && !m_storageAreaSync && m_storageSyncManager) {
     303        m_storageAreaSync = StorageAreaSync::create(m_storageSyncManager.get(), *this, m_securityOrigin.databaseIdentifier());
     304        return;
     305    }
     306
     307    if (!isNewSessionPersistent && m_storageAreaSync) {
     308        m_storageAreaSync->scheduleFinalSync();
     309        m_storageAreaSync = nullptr;
     310    }
     311}
     312
    295313} // namespace WebCore
  • trunk/Source/WebKitLegacy/Storage/StorageAreaImpl.h

    r247486 r248734  
    6262    void closeDatabaseIfIdle() override;
    6363
    64     const WebCore::SecurityOriginData& securityOrigin() const override { return m_securityOrigin; }
    65 
    6664    Ref<StorageAreaImpl> copy();
    6765    void close();
    … …  
    7472
    7573    void sync();
     74
     75    void sessionChanged(bool isNewSessionPersistent);
    7676
    7777private:
  • trunk/Source/WebKitLegacy/Storage/StorageAreaSync.h

    r208499 r248734  
    4040class StorageAreaImpl;
    4141
    42 class StorageAreaSync : public ThreadSafeRefCounted<StorageAreaSync> {
     42class StorageAreaSync : public ThreadSafeRefCounted<StorageAreaSync, WTF::DestructionThread::Main> {
    4343public:
    4444    static Ref<StorageAreaSync> create(RefPtr<WebCore::StorageSyncManager>&&, Ref<StorageAreaImpl>&&, const String& databaseIdentifier);
  • trunk/Source/WebKitLegacy/Storage/StorageNamespaceImpl.cpp

    r239535 r248734  
    4646}
    4747
    48 Ref<StorageNamespaceImpl> StorageNamespaceImpl::createSessionStorageNamespace(unsigned quota)
     48Ref<StorageNamespaceImpl> StorageNamespaceImpl::createSessionStorageNamespace(unsigned quota, PAL::SessionID sessionID)
    4949{
    50     return adoptRef(*new StorageNamespaceImpl(StorageType::Session, String(), quota));
     50    return adoptRef(*new StorageNamespaceImpl(StorageType::Session, String(), quota, sessionID));
    5151}
    5252
    53 Ref<StorageNamespaceImpl> StorageNamespaceImpl::createEphemeralLocalStorageNamespace(unsigned quota)
    54 {
    55     return adoptRef(*new StorageNamespaceImpl(StorageType::EphemeralLocal, String(), quota));
    56 }
    57 
    58 Ref<StorageNamespaceImpl> StorageNamespaceImpl::getOrCreateLocalStorageNamespace(const String& databasePath, unsigned quota)
     53Ref<StorageNamespaceImpl> StorageNamespaceImpl::getOrCreateLocalStorageNamespace(const String& databasePath, unsigned quota, PAL::SessionID sessionID)
    5954{
    6055    ASSERT(!databasePath.isNull());
    … …  
    6459        return *slot;
    6560
    66     Ref<StorageNamespaceImpl> storageNamespace = adoptRef(*new StorageNamespaceImpl(StorageType::Local, databasePath, quota));
     61    Ref<StorageNamespaceImpl> storageNamespace = adoptRef(*new StorageNamespaceImpl(StorageType::Local, databasePath, quota, sessionID));
    6762    slot = storageNamespace.ptr();
    6863
    … …  
    7065}
    7166
    72 StorageNamespaceImpl::StorageNamespaceImpl(StorageType storageType, const String& path, unsigned quota)
     67StorageNamespaceImpl::StorageNamespaceImpl(StorageType storageType, const String& path, unsigned quota, PAL::SessionID sessionID)
    7368    : m_storageType(storageType)
    7469    , m_path(path.isolatedCopy())
    … …  
    7671    , m_quota(quota)
    7772    , m_isShutdown(false)
     73    , m_sessionID(sessionID)
    7874{
    7975    if (isPersistentLocalStorage(m_storageType) && !m_path.isEmpty())
    … …  
    9894    ASSERT(isMainThread());
    9995    ASSERT(!m_isShutdown);
    100     ASSERT(m_storageType == StorageType::Session || m_storageType == StorageType::EphemeralLocal);
     96    ASSERT(m_storageType == StorageType::Session);
    10197
    102     auto newNamespace = adoptRef(*new StorageNamespaceImpl(m_storageType, m_path, m_quota));
     98    auto newNamespace = adoptRef(*new StorageNamespaceImpl(m_storageType, m_path, m_quota, m_sessionID));
    10399    for (auto& iter : m_storageAreaMap)
    104100        newNamespace->m_storageAreaMap.set(iter.key, iter.value->copy());
    … …  
    128124
    129125    // If we're not a persistent storage, we shouldn't need to do any work here.
    130     if (m_storageType == StorageType::Session || m_storageType == StorageType::EphemeralLocal) {
     126    if (m_storageType == StorageType::Session) {
    131127        ASSERT(!m_syncManager);
    132128        return;
    … …  
    177173}
    178174
     175void StorageNamespaceImpl::setSessionIDForTesting(PAL::SessionID sessionID)
     176{
     177    m_sessionID = sessionID;
     178    for (auto storageAreaMap : m_storageAreaMap.values())
     179        storageAreaMap->sessionChanged(!sessionID.isEphemeral());
     180}
     181
    179182} // namespace WebCore
  • trunk/Source/WebKitLegacy/Storage/StorageNamespaceImpl.h

    r239535 r248734  
    2929#include <WebCore/StorageArea.h>
    3030#include <WebCore/StorageNamespace.h>
     31#include <pal/SessionID.h>
    3132#include <wtf/HashMap.h>
    3233#include <wtf/RefPtr.h>
    … …  
    3940class StorageNamespaceImpl : public WebCore::StorageNamespace {
    4041public:
    41     static Ref<StorageNamespaceImpl> createSessionStorageNamespace(unsigned quota);
    42     static Ref<StorageNamespaceImpl> createEphemeralLocalStorageNamespace(unsigned quota);
    43     static Ref<StorageNamespaceImpl> getOrCreateLocalStorageNamespace(const String& databasePath, unsigned quota);
     42    static Ref<StorageNamespaceImpl> createSessionStorageNamespace(unsigned quota, PAL::SessionID);
     43    static Ref<StorageNamespaceImpl> getOrCreateLocalStorageNamespace(const String& databasePath, unsigned quota, PAL::SessionID);
    4444    virtual ~StorageNamespaceImpl();
    4545
    … …  
    5555    void closeIdleLocalStorageDatabases();
    5656
     57    PAL::SessionID sessionID() const override { return m_sessionID; }
     58    void setSessionIDForTesting(PAL::SessionID) override;
     59
    5760private:
    58     StorageNamespaceImpl(WebCore::StorageType, const String& path, unsigned quota);
     61    StorageNamespaceImpl(WebCore::StorageType, const String& path, unsigned quota, PAL::SessionID);
    5962
    6063    Ref<WebCore::StorageArea> storageArea(const WebCore::SecurityOriginData&) override;
    … …  
    7477
    7578    bool m_isShutdown;
     79
     80    PAL::SessionID m_sessionID;
    7681};
    7782
  • trunk/Source/WebKitLegacy/Storage/WebStorageNamespaceProvider.cpp

    r239535 r248734  
    2727
    2828#include "StorageNamespaceImpl.h"
     29#include <WebCore/Page.h>
    2930#include <wtf/NeverDestroyed.h>
    3031
    … …  
    9798}
    9899
    99 Ref<StorageNamespace> WebStorageNamespaceProvider::createSessionStorageNamespace(Page&, unsigned quota)
     100Ref<StorageNamespace> WebStorageNamespaceProvider::createSessionStorageNamespace(Page& page, unsigned quota)
    100101{
    101     return StorageNamespaceImpl::createSessionStorageNamespace(quota);
     102    return StorageNamespaceImpl::createSessionStorageNamespace(quota, page.sessionID());
    102103}
    103104
    104 Ref<StorageNamespace> WebStorageNamespaceProvider::createEphemeralLocalStorageNamespace(Page&, unsigned quota)
     105Ref<StorageNamespace> WebStorageNamespaceProvider::createLocalStorageNamespace(unsigned quota, PAL::SessionID sessionID)
    105106{
    106     return StorageNamespaceImpl::createEphemeralLocalStorageNamespace(quota);
     107    return StorageNamespaceImpl::getOrCreateLocalStorageNamespace(m_localStorageDatabasePath, quota, sessionID);
    107108}
    108109
    109 Ref<StorageNamespace> WebStorageNamespaceProvider::createLocalStorageNamespace(unsigned quota)
    110 {
    111     return StorageNamespaceImpl::getOrCreateLocalStorageNamespace(m_localStorageDatabasePath, quota);
    112 }
    113 
    114 Ref<StorageNamespace> WebStorageNamespaceProvider::createTransientLocalStorageNamespace(SecurityOrigin&, unsigned quota)
     110Ref<StorageNamespace> WebStorageNamespaceProvider::createTransientLocalStorageNamespace(SecurityOrigin&, unsigned quota, PAL::SessionID sessionID)
    115111{
    116112    // FIXME: A smarter implementation would create a special namespace type instead of just piggy-backing off
    117113    // SessionStorageNamespace here.
    118     return StorageNamespaceImpl::createSessionStorageNamespace(quota);
     114    return StorageNamespaceImpl::createSessionStorageNamespace(quota, sessionID);
    119115}
    120116
  • trunk/Source/WebKitLegacy/Storage/WebStorageNamespaceProvider.h

    r239535 r248734  
    5151
    5252    Ref<WebCore::StorageNamespace> createSessionStorageNamespace(WebCore::Page&, unsigned quota) override;
    53     Ref<WebCore::StorageNamespace> createEphemeralLocalStorageNamespace(WebCore::Page&, unsigned quota) override;
    54     Ref<WebCore::StorageNamespace> createLocalStorageNamespace(unsigned quota) override;
    55     Ref<WebCore::StorageNamespace> createTransientLocalStorageNamespace(WebCore::SecurityOrigin&, unsigned quota) override;
     53    Ref<WebCore::StorageNamespace> createLocalStorageNamespace(unsigned quota, PAL::SessionID) override;
     54    Ref<WebCore::StorageNamespace> createTransientLocalStorageNamespace(WebCore::SecurityOrigin&, unsigned quota, PAL::SessionID) override;
    5655
    5756    const String m_localStorageDatabasePath;
  • trunk/Source/WebKitLegacy/mac/ChangeLog

    r248728 r248734  
     12019-08-15  Sihui Liu  <sihui_liu@apple.com>
     2
     3        Some improvements on web storage
     4        https://bugs.webkit.org/show_bug.cgi?id=200373
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        * WebView/WebView.mm:
     9        (-[WebView _preferencesChanged:]): notify storageNamespaceProvider about session change.
     10
    1112019-08-15  Youenn Fablet  <youenn@apple.com>
    212
  • trunk/Source/WebKitLegacy/mac/WebView/WebView.mm

    r248697 r248734  
    28892889
    28902890    _private->page->enableLegacyPrivateBrowsing([preferences privateBrowsingEnabled]);
     2891    _private->group->storageNamespaceProvider().enableLegacyPrivateBrowsingForTesting([preferences privateBrowsingEnabled]);
    28912892    settings.setSansSerifFontFamily([preferences sansSerifFontFamily]);
    28922893    settings.setSerifFontFamily([preferences serifFontFamily]);
  • trunk/Tools/ChangeLog

    r248727 r248734  
     12019-08-15  Sihui Liu  <sihui_liu@apple.com>
     2
     3        Some improvements on web storage
     4        https://bugs.webkit.org/show_bug.cgi?id=200373
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        * TestWebKitAPI/Tests/WebKitCocoa/LocalStoragePersistence.mm:
     9        (TEST): update expectation for behavior change.
     10
     11        * WebKitTestRunner/InjectedBundle/Bindings/TestRunner.idl: new SPI to synchronously flush localStorage to
     12        database file.
     13        * WebKitTestRunner/InjectedBundle/TestRunner.cpp:
     14        (WTR::TestRunner::syncLocalStorage):
     15        * WebKitTestRunner/InjectedBundle/TestRunner.h:
     16
     17        * WebKitTestRunner/TestController.cpp: clear local storage between test runs to make each test isolated.
     18        (WTR::TestController::resetStateToConsistentValues):
     19        (WTR::StorageVoidCallbackContext::StorageVoidCallbackContext):
     20        (WTR::StorageVoidCallback):
     21        (WTR::TestController::clearIndexedDatabases):
     22        (WTR::TestController::clearLocalStorage):
     23        (WTR::TestController::syncLocalStorage):
     24        (WTR::RemoveAllIndexedDatabasesCallbackContext::RemoveAllIndexedDatabasesCallbackContext): Deleted. Replaced
     25        with StorageVoidCallbackContext for general usage.
     26        (WTR::RemoveAllIndexedDatabasesCallback): Deleted. Replaced with StorageVoidCallback.
     27        (WTR::TestController::ClearIndexedDatabases): Deleted. Use lowercase for consistent style.
     28        * WebKitTestRunner/TestController.h:
     29
     30        * WebKitTestRunner/TestInvocation.cpp:
     31        (WTR::TestInvocation::didReceiveSynchronousMessageFromInjectedBundle): add handler for new message
     32        SyncLocalStorage.
     33
    1342019-08-15  Jonathan Bedard  <jbedard@apple.com>
    235
  • trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/LocalStoragePersistence.mm

    r248047 r248734  
    105105    TestWebKitAPI::Util::run(&readyToContinue);
    106106
     107    // If network process crashes, sessionStorage would be lost.
    107108    readyToContinue = false;
    108109    [webView evaluateJavaScript:@"window.sessionStorage.getItem('session')" completionHandler:^(id result, NSError *) {
    109         EXPECT_TRUE([@"storage" isEqualToString:result]);
     110        EXPECT_TRUE([result isEqual:NSNull.null]);
    110111        readyToContinue = true;
    111112    }];
  • trunk/Tools/WebKitTestRunner/InjectedBundle/Bindings/TestRunner.idl

    r248699 r248734  
    143143    void setDatabaseQuota(unsigned long long quota);
    144144    DOMString pathToLocalResource(DOMString url);
     145    void syncLocalStorage();
    145146
    146147    attribute double databaseDefaultQuota;
  • trunk/Tools/WebKitTestRunner/InjectedBundle/TestRunner.cpp

    r248699 r248734  
    343343}
    344344
     345void TestRunner::syncLocalStorage()
     346{
     347    WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("SyncLocalStorage"));
     348    WKRetainPtr<WKBooleanRef> messageBody = adoptWK(WKBooleanCreate(true));
     349    WKBundlePostSynchronousMessage(InjectedBundle::singleton().bundle(), messageName.get(), messageBody.get(), nullptr);
     350}
     351
    345352void TestRunner::clearAllApplicationCaches()
    346353{
  • trunk/Tools/WebKitTestRunner/InjectedBundle/TestRunner.h

    r248699 r248734  
    160160    void setDatabaseQuota(uint64_t);
    161161    JSRetainPtr<JSStringRef> pathToLocalResource(JSStringRef);
     162    void syncLocalStorage();
    162163
    163164    // Application Cache
  • trunk/Tools/WebKitTestRunner/TestController.cpp

    r248699 r248734  
    940940    WKWebsiteDataStoreClearAllDeviceOrientationPermissions(websiteDataStore);
    941941
    942     ClearIndexedDatabases();
    943942    setIDBPerOriginQuota(50 * MB);
     943
     944    clearIndexedDatabases();
     945    clearLocalStorage();
    944946
    945947    clearServiceWorkerRegistrations();
    … …  
    30703072}
    30713073
    3072 struct RemoveAllIndexedDatabasesCallbackContext {
    3073     explicit RemoveAllIndexedDatabasesCallbackContext(TestController& controller)
     3074struct StorageVoidCallbackContext {
     3075    explicit StorageVoidCallbackContext(TestController& controller)
    30743076        : testController(controller)
    30753077    {
    … …  
    30803082};
    30813083
    3082 static void RemoveAllIndexedDatabasesCallback(void* userData)
    3083 {
    3084     auto* context = static_cast<RemoveAllIndexedDatabasesCallbackContext*>(userData);
     3084static void StorageVoidCallback(void* userData)
     3085{
     3086    auto* context = static_cast<StorageVoidCallbackContext*>(userData);
    30853087    context->done = true;
    30863088    context->testController.notifyDone();
    30873089}
    30883090
    3089 void TestController::ClearIndexedDatabases()
     3091void TestController::clearIndexedDatabases()
    30903092{
    30913093    auto websiteDataStore = WKContextGetWebsiteDataStore(platformContext());
    3092     RemoveAllIndexedDatabasesCallbackContext context(*this);
    3093     WKWebsiteDataStoreRemoveAllIndexedDatabases(websiteDataStore, &context, RemoveAllIndexedDatabasesCallback);
     3094    StorageVoidCallbackContext context(*this);
     3095    WKWebsiteDataStoreRemoveAllIndexedDatabases(websiteDataStore, &context, StorageVoidCallback);
     3096    runUntil(context.done, noTimeout);
     3097}
     3098
     3099void TestController::clearLocalStorage()
     3100{
     3101    auto websiteDataStore = WKContextGetWebsiteDataStore(platformContext());
     3102    StorageVoidCallbackContext context(*this);
     3103    WKWebsiteDataStoreRemoveLocalStorage(websiteDataStore, &context, StorageVoidCallback);
     3104    runUntil(context.done, noTimeout);
     3105
     3106    StorageVoidCallbackContext legacyContext(*this);
     3107    WKContextClearLegacyPrivateBrowsingLocalStorage(platformContext(), &legacyContext, StorageVoidCallback);
     3108    runUntil(legacyContext.done, noTimeout);
     3109}
     3110
     3111void TestController::syncLocalStorage()
     3112{
     3113    StorageVoidCallbackContext context(*this);
     3114    WKContextSyncLocalStorage(platformContext(), &context, StorageVoidCallback);
    30943115    runUntil(context.done, noTimeout);
    30953116}
  • trunk/Tools/WebKitTestRunner/TestController.h

    r248699 r248734  
    263263    void removeAllSessionCredentials();
    264264
    265     void ClearIndexedDatabases();
     265    void clearIndexedDatabases();
     266    void clearLocalStorage();
     267    void syncLocalStorage();
    266268
    267269    void clearServiceWorkerRegistrations();
  • trunk/Tools/WebKitTestRunner/TestInvocation.cpp

    r248699 r248734  
    16671667    }
    16681668
     1669    if (WKStringIsEqualToUTF8CString(messageName, "SyncLocalStorage")) {
     1670        TestController::singleton().syncLocalStorage();
     1671        return nullptr;
     1672    }
     1673
    16691674    ASSERT_NOT_REACHED();
    16701675    return nullptr;
Note: See TracChangeset for help on using the changeset viewer.