зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1719281 - QM: Add a generic wrapper for running initializations; r=dom-storage-reviewers,asuth
Differential Revision: https://phabricator.services.mozilla.com/D119182
This commit is contained in:
Родитель
edbd3850d8
Коммит
f269c78d92
|
@ -3096,6 +3096,22 @@ bool VerifyOriginKey(const nsACString& aOriginKey,
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
LSInitializationInfo& MutableInitializationInfoRef(const CreateIfNonExistent&) {
|
||||||
|
if (!gInitializationInfo) {
|
||||||
|
gInitializationInfo = new LSInitializationInfo();
|
||||||
|
}
|
||||||
|
return *gInitializationInfo;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult ExecuteOriginInitialization(
|
||||||
|
const nsACString& aOrigin, const LSOriginInitialization aInitialization,
|
||||||
|
const nsresult aRv) {
|
||||||
|
return ExecuteInitialization(
|
||||||
|
MutableInitializationInfoRef(CreateIfNonExistent{})
|
||||||
|
.MutableOriginInitializationInfoRef(aOrigin, CreateIfNonExistent{}),
|
||||||
|
aInitialization, aRv);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
|
@ -6781,24 +6797,16 @@ nsresult PrepareDatastoreOp::DatabaseWork() {
|
||||||
MOZ_ASSERT(mState == State::Nesting);
|
MOZ_ASSERT(mState == State::Nesting);
|
||||||
MOZ_ASSERT(mNestedState == NestedState::DatabaseWorkOpen);
|
MOZ_ASSERT(mNestedState == NestedState::DatabaseWorkOpen);
|
||||||
|
|
||||||
// XXX Maybe add GetOrCreateInitializationInfo for this.
|
const auto innerFunc = [this]() -> nsresult {
|
||||||
if (!gInitializationInfo) {
|
|
||||||
gInitializationInfo = new LSInitializationInfo();
|
|
||||||
}
|
|
||||||
|
|
||||||
auto& originInitializationInfo =
|
|
||||||
gInitializationInfo->MutableOriginInitializationInfoRef(
|
|
||||||
mOriginMetadata.mOrigin);
|
|
||||||
|
|
||||||
const auto firstInitializationAttempt =
|
|
||||||
originInitializationInfo.FirstInitializationAttempt(
|
|
||||||
LSOriginInitialization::Datastore);
|
|
||||||
|
|
||||||
auto rv = [&firstInitializationAttempt, this]() -> nsresult {
|
|
||||||
// XXX This function is too long, refactor it into helper functions for
|
// XXX This function is too long, refactor it into helper functions for
|
||||||
// readability.
|
// readability.
|
||||||
|
|
||||||
const auto maybeExtraInfo =
|
const auto maybeExtraInfo =
|
||||||
firstInitializationAttempt.Pending()
|
MutableInitializationInfoRef(CreateIfNonExistent{})
|
||||||
|
.MutableOriginInitializationInfoRef(mOriginMetadata.mOrigin,
|
||||||
|
CreateIfNonExistent{})
|
||||||
|
.FirstInitializationAttemptPending(
|
||||||
|
LSOriginInitialization::Datastore)
|
||||||
? Some(ScopedLogExtraInfo{
|
? Some(ScopedLogExtraInfo{
|
||||||
ScopedLogExtraInfo::kTagContext,
|
ScopedLogExtraInfo::kTagContext,
|
||||||
"dom::localstorage::FirstOriginInitializationAttempt::Datastore"_ns})
|
"dom::localstorage::FirstOriginInitializationAttempt::Datastore"_ns})
|
||||||
|
@ -7052,11 +7060,10 @@ nsresult PrepareDatastoreOp::DatabaseWork() {
|
||||||
QM_TRY(OwningEventTarget()->Dispatch(this, NS_DISPATCH_NORMAL));
|
QM_TRY(OwningEventTarget()->Dispatch(this, NS_DISPATCH_NORMAL));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
firstInitializationAttempt.MaybeRecord(rv);
|
return ExecuteOriginInitialization(
|
||||||
|
mOriginMetadata.mOrigin, LSOriginInitialization::Datastore, innerFunc());
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult PrepareDatastoreOp::DatabaseNotAvailable() {
|
nsresult PrepareDatastoreOp::DatabaseNotAvailable() {
|
||||||
|
|
|
@ -11,6 +11,10 @@
|
||||||
#include <mozilla/dom/quota/FirstInitializationAttempts.h>
|
#include <mozilla/dom/quota/FirstInitializationAttempts.h>
|
||||||
#include "nsTHashMap.h"
|
#include "nsTHashMap.h"
|
||||||
|
|
||||||
|
namespace mozilla {
|
||||||
|
struct CreateIfNonExistent;
|
||||||
|
}
|
||||||
|
|
||||||
namespace mozilla::dom {
|
namespace mozilla::dom {
|
||||||
|
|
||||||
enum class LSOriginInitialization {
|
enum class LSOriginInitialization {
|
||||||
|
@ -29,7 +33,7 @@ class LSInitializationInfo final {
|
||||||
|
|
||||||
public:
|
public:
|
||||||
LSOriginInitializationInfo& MutableOriginInitializationInfoRef(
|
LSOriginInitializationInfo& MutableOriginInitializationInfoRef(
|
||||||
const nsACString& aOrigin) {
|
const nsACString& aOrigin, const CreateIfNonExistent&) {
|
||||||
return mOriginInitializationInfos.LookupOrInsert(aOrigin);
|
return mOriginInitializationInfos.LookupOrInsert(aOrigin);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -4238,13 +4238,15 @@ nsresult QuotaManager::LoadQuota() {
|
||||||
|
|
||||||
QM_TRY(([&]() -> Result<Ok, nsresult> {
|
QM_TRY(([&]() -> Result<Ok, nsresult> {
|
||||||
QM_TRY(([this, type] {
|
QM_TRY(([this, type] {
|
||||||
const nsresult rv = InitializeRepository(type);
|
const auto innerFunc = [type, this]() -> nsresult {
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return InitializeRepository(type);
|
||||||
|
};
|
||||||
|
|
||||||
|
return ExecuteInitialization(
|
||||||
type == PERSISTENCE_TYPE_DEFAULT
|
type == PERSISTENCE_TYPE_DEFAULT
|
||||||
? Initialization::DefaultRepository
|
? Initialization::DefaultRepository
|
||||||
: Initialization::TemporaryRepository,
|
: Initialization::TemporaryRepository,
|
||||||
rv);
|
innerFunc());
|
||||||
return rv;
|
|
||||||
}()),
|
}()),
|
||||||
OK_IN_NIGHTLY_PROPAGATE_IN_OTHERS, statusKeeperFunc);
|
OK_IN_NIGHTLY_PROPAGATE_IN_OTHERS, statusKeeperFunc);
|
||||||
|
|
||||||
|
@ -5006,7 +5008,7 @@ QuotaManager::UpgradeFromIndexedDBDirectoryToPersistentStorageDirectory(
|
||||||
AssertIsOnIOThread();
|
AssertIsOnIOThread();
|
||||||
MOZ_ASSERT(aIndexedDBDir);
|
MOZ_ASSERT(aIndexedDBDir);
|
||||||
|
|
||||||
auto rv = [this, &aIndexedDBDir]() -> nsresult {
|
const auto innerFunc = [this, &aIndexedDBDir]() -> nsresult {
|
||||||
bool isDirectory;
|
bool isDirectory;
|
||||||
QM_TRY(aIndexedDBDir->IsDirectory(&isDirectory));
|
QM_TRY(aIndexedDBDir->IsDirectory(&isDirectory));
|
||||||
|
|
||||||
|
@ -5049,12 +5051,10 @@ QuotaManager::UpgradeFromIndexedDBDirectoryToPersistentStorageDirectory(
|
||||||
nsLiteralString(PERSISTENT_DIRECTORY_NAME)));
|
nsLiteralString(PERSISTENT_DIRECTORY_NAME)));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return ExecuteInitialization(Initialization::UpgradeFromIndexedDBDirectory,
|
||||||
Initialization::UpgradeFromIndexedDBDirectory, rv);
|
innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult
|
nsresult
|
||||||
|
@ -5063,7 +5063,7 @@ QuotaManager::UpgradeFromPersistentStorageDirectoryToDefaultStorageDirectory(
|
||||||
AssertIsOnIOThread();
|
AssertIsOnIOThread();
|
||||||
MOZ_ASSERT(aPersistentStorageDir);
|
MOZ_ASSERT(aPersistentStorageDir);
|
||||||
|
|
||||||
auto rv = [this, &aPersistentStorageDir]() -> nsresult {
|
const auto innerFunc = [this, &aPersistentStorageDir]() -> nsresult {
|
||||||
QM_TRY_INSPECT(const bool& isDirectory,
|
QM_TRY_INSPECT(const bool& isDirectory,
|
||||||
MOZ_TO_RESULT_INVOKE(aPersistentStorageDir, IsDirectory));
|
MOZ_TO_RESULT_INVOKE(aPersistentStorageDir, IsDirectory));
|
||||||
|
|
||||||
|
@ -5128,12 +5128,9 @@ QuotaManager::UpgradeFromPersistentStorageDirectoryToDefaultStorageDirectory(
|
||||||
nullptr, nsLiteralString(DEFAULT_DIRECTORY_NAME)));
|
nullptr, nsLiteralString(DEFAULT_DIRECTORY_NAME)));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
return ExecuteInitialization(
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
Initialization::UpgradeFromPersistentStorageDirectory, innerFunc());
|
||||||
Initialization::UpgradeFromPersistentStorageDirectory, rv);
|
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename Helper>
|
template <typename Helper>
|
||||||
|
@ -5181,17 +5178,15 @@ nsresult QuotaManager::UpgradeStorageFrom0_0To1_0(
|
||||||
AssertIsOnIOThread();
|
AssertIsOnIOThread();
|
||||||
MOZ_ASSERT(aConnection);
|
MOZ_ASSERT(aConnection);
|
||||||
|
|
||||||
auto rv = [this, &aConnection]() -> nsresult {
|
const auto innerFunc = [this, &aConnection]() -> nsresult {
|
||||||
QM_TRY(UpgradeStorage<UpgradeStorageFrom0_0To1_0Helper>(
|
QM_TRY(UpgradeStorage<UpgradeStorageFrom0_0To1_0Helper>(
|
||||||
0, MakeStorageVersion(1, 0), aConnection));
|
0, MakeStorageVersion(1, 0), aConnection));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return ExecuteInitialization(Initialization::UpgradeStorageFrom0_0To1_0,
|
||||||
Initialization::UpgradeStorageFrom0_0To1_0, rv);
|
innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult QuotaManager::UpgradeStorageFrom1_0To2_0(
|
nsresult QuotaManager::UpgradeStorageFrom1_0To2_0(
|
||||||
|
@ -5266,17 +5261,15 @@ nsresult QuotaManager::UpgradeStorageFrom1_0To2_0(
|
||||||
// manager directories without the ".files" suffix then prevent current
|
// manager directories without the ".files" suffix then prevent current
|
||||||
// Firefox from initializing and using the storage.
|
// Firefox from initializing and using the storage.
|
||||||
|
|
||||||
auto rv = [this, &aConnection]() -> nsresult {
|
const auto innerFunc = [this, &aConnection]() -> nsresult {
|
||||||
QM_TRY(UpgradeStorage<UpgradeStorageFrom1_0To2_0Helper>(
|
QM_TRY(UpgradeStorage<UpgradeStorageFrom1_0To2_0Helper>(
|
||||||
MakeStorageVersion(1, 0), MakeStorageVersion(2, 0), aConnection));
|
MakeStorageVersion(1, 0), MakeStorageVersion(2, 0), aConnection));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return ExecuteInitialization(Initialization::UpgradeStorageFrom1_0To2_0,
|
||||||
Initialization::UpgradeStorageFrom1_0To2_0, rv);
|
innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult QuotaManager::UpgradeStorageFrom2_0To2_1(
|
nsresult QuotaManager::UpgradeStorageFrom2_0To2_1(
|
||||||
|
@ -5287,17 +5280,15 @@ nsresult QuotaManager::UpgradeStorageFrom2_0To2_1(
|
||||||
// The upgrade is mainly to create a directory padding file in DOM Cache
|
// The upgrade is mainly to create a directory padding file in DOM Cache
|
||||||
// directory to record the overall padding size of an origin.
|
// directory to record the overall padding size of an origin.
|
||||||
|
|
||||||
auto rv = [this, &aConnection]() -> nsresult {
|
const auto innerFunc = [this, &aConnection]() -> nsresult {
|
||||||
QM_TRY(UpgradeStorage<UpgradeStorageFrom2_0To2_1Helper>(
|
QM_TRY(UpgradeStorage<UpgradeStorageFrom2_0To2_1Helper>(
|
||||||
MakeStorageVersion(2, 0), MakeStorageVersion(2, 1), aConnection));
|
MakeStorageVersion(2, 0), MakeStorageVersion(2, 1), aConnection));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return ExecuteInitialization(Initialization::UpgradeStorageFrom2_0To2_1,
|
||||||
Initialization::UpgradeStorageFrom2_0To2_1, rv);
|
innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult QuotaManager::UpgradeStorageFrom2_1To2_2(
|
nsresult QuotaManager::UpgradeStorageFrom2_1To2_2(
|
||||||
|
@ -5308,17 +5299,15 @@ nsresult QuotaManager::UpgradeStorageFrom2_1To2_2(
|
||||||
// The upgrade is mainly to clean obsolete origins in the repositoies, remove
|
// The upgrade is mainly to clean obsolete origins in the repositoies, remove
|
||||||
// asmjs client, and ".tmp" file in the idb folers.
|
// asmjs client, and ".tmp" file in the idb folers.
|
||||||
|
|
||||||
auto rv = [this, &aConnection]() -> nsresult {
|
const auto innerFunc = [this, &aConnection]() -> nsresult {
|
||||||
QM_TRY(UpgradeStorage<UpgradeStorageFrom2_1To2_2Helper>(
|
QM_TRY(UpgradeStorage<UpgradeStorageFrom2_1To2_2Helper>(
|
||||||
MakeStorageVersion(2, 1), MakeStorageVersion(2, 2), aConnection));
|
MakeStorageVersion(2, 1), MakeStorageVersion(2, 2), aConnection));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return ExecuteInitialization(Initialization::UpgradeStorageFrom2_1To2_2,
|
||||||
Initialization::UpgradeStorageFrom2_1To2_2, rv);
|
innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult QuotaManager::UpgradeStorageFrom2_2To2_3(
|
nsresult QuotaManager::UpgradeStorageFrom2_2To2_3(
|
||||||
|
@ -5326,7 +5315,7 @@ nsresult QuotaManager::UpgradeStorageFrom2_2To2_3(
|
||||||
AssertIsOnIOThread();
|
AssertIsOnIOThread();
|
||||||
MOZ_ASSERT(aConnection);
|
MOZ_ASSERT(aConnection);
|
||||||
|
|
||||||
auto rv = [&aConnection]() -> nsresult {
|
const auto innerFunc = [&aConnection]() -> nsresult {
|
||||||
// Table `database`
|
// Table `database`
|
||||||
QM_TRY(aConnection->ExecuteSimpleSQL(
|
QM_TRY(aConnection->ExecuteSimpleSQL(
|
||||||
nsLiteralCString("CREATE TABLE database"
|
nsLiteralCString("CREATE TABLE database"
|
||||||
|
@ -5349,12 +5338,10 @@ nsresult QuotaManager::UpgradeStorageFrom2_2To2_3(
|
||||||
QM_TRY(aConnection->SetSchemaVersion(MakeStorageVersion(2, 3)));
|
QM_TRY(aConnection->SetSchemaVersion(MakeStorageVersion(2, 3)));
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
mInitializationInfo.MaybeRecordFirstInitializationAttempt(
|
return ExecuteInitialization(Initialization::UpgradeStorageFrom2_2To2_3,
|
||||||
Initialization::UpgradeStorageFrom2_2To2_3, rv);
|
innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult QuotaManager::MaybeRemoveLocalStorageDataAndArchive(
|
nsresult QuotaManager::MaybeRemoveLocalStorageDataAndArchive(
|
||||||
|
@ -5996,15 +5983,10 @@ Result<Ok, nsresult> QuotaManager::CreateEmptyLocalStorageArchive(
|
||||||
nsresult QuotaManager::EnsureStorageIsInitialized() {
|
nsresult QuotaManager::EnsureStorageIsInitialized() {
|
||||||
DiagnosticAssertIsOnIOThread();
|
DiagnosticAssertIsOnIOThread();
|
||||||
|
|
||||||
const auto firstInitializationAttempt =
|
const auto innerFunc = [this]() -> nsresult {
|
||||||
mInitializationInfo.FirstInitializationAttempt(Initialization::Storage);
|
const auto firstInitializationAttempt =
|
||||||
|
mInitializationInfo.FirstInitializationAttempt(Initialization::Storage);
|
||||||
|
|
||||||
if (mStorageConnection) {
|
|
||||||
MOZ_ASSERT(firstInitializationAttempt.Recorded());
|
|
||||||
return NS_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto rv = [&firstInitializationAttempt, this]() -> nsresult {
|
|
||||||
const auto maybeExtraInfo =
|
const auto maybeExtraInfo =
|
||||||
firstInitializationAttempt.Pending()
|
firstInitializationAttempt.Pending()
|
||||||
? Some(ScopedLogExtraInfo{
|
? Some(ScopedLogExtraInfo{
|
||||||
|
@ -6012,6 +5994,11 @@ nsresult QuotaManager::EnsureStorageIsInitialized() {
|
||||||
"dom::quota::FirstInitializationAttempt::Storage"_ns})
|
"dom::quota::FirstInitializationAttempt::Storage"_ns})
|
||||||
: Nothing{};
|
: Nothing{};
|
||||||
|
|
||||||
|
if (mStorageConnection) {
|
||||||
|
MOZ_ASSERT(firstInitializationAttempt.Recorded());
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
QM_TRY_INSPECT(const auto& storageFile, QM_NewLocalFile(mBasePath));
|
QM_TRY_INSPECT(const auto& storageFile, QM_NewLocalFile(mBasePath));
|
||||||
QM_TRY(storageFile->Append(mStorageName + kSQLiteSuffix));
|
QM_TRY(storageFile->Append(mStorageName + kSQLiteSuffix));
|
||||||
|
|
||||||
|
@ -6077,11 +6064,9 @@ nsresult QuotaManager::EnsureStorageIsInitialized() {
|
||||||
mStorageConnection = std::move(connection);
|
mStorageConnection = std::move(connection);
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
firstInitializationAttempt.MaybeRecord(rv);
|
return ExecuteInitialization(Initialization::Storage, innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
RefPtr<ClientDirectoryLock> QuotaManager::CreateDirectoryLock(
|
RefPtr<ClientDirectoryLock> QuotaManager::CreateDirectoryLock(
|
||||||
|
@ -6111,16 +6096,14 @@ QuotaManager::EnsurePersistentOriginIsInitialized(
|
||||||
MOZ_ASSERT(aOriginMetadata.mPersistenceType == PERSISTENCE_TYPE_PERSISTENT);
|
MOZ_ASSERT(aOriginMetadata.mPersistenceType == PERSISTENCE_TYPE_PERSISTENT);
|
||||||
MOZ_DIAGNOSTIC_ASSERT(mStorageConnection);
|
MOZ_DIAGNOSTIC_ASSERT(mStorageConnection);
|
||||||
|
|
||||||
auto& originInitializationInfo =
|
const auto innerFunc = [&aOriginMetadata, this]()
|
||||||
mInitializationInfo.MutableOriginInitializationInfoRef(
|
|
||||||
aOriginMetadata.mOrigin);
|
|
||||||
|
|
||||||
const auto firstInitializationAttempt =
|
|
||||||
originInitializationInfo.FirstInitializationAttempt(
|
|
||||||
OriginInitialization::PersistentOrigin);
|
|
||||||
|
|
||||||
auto res = [&firstInitializationAttempt, &aOriginMetadata, this]()
|
|
||||||
-> mozilla::Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult> {
|
-> mozilla::Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult> {
|
||||||
|
const auto firstInitializationAttempt =
|
||||||
|
mInitializationInfo
|
||||||
|
.MutableOriginInitializationInfoRef(aOriginMetadata.mOrigin,
|
||||||
|
CreateIfNonExistent{})
|
||||||
|
.FirstInitializationAttempt(OriginInitialization::PersistentOrigin);
|
||||||
|
|
||||||
const auto maybeExtraInfo =
|
const auto maybeExtraInfo =
|
||||||
firstInitializationAttempt.Pending()
|
firstInitializationAttempt.Pending()
|
||||||
? Some(ScopedLogExtraInfo{
|
? Some(ScopedLogExtraInfo{
|
||||||
|
@ -6133,6 +6116,7 @@ QuotaManager::EnsurePersistentOriginIsInitialized(
|
||||||
aOriginMetadata.mOrigin));
|
aOriginMetadata.mOrigin));
|
||||||
|
|
||||||
if (mInitializedOrigins.Contains(aOriginMetadata.mOrigin)) {
|
if (mInitializedOrigins.Contains(aOriginMetadata.mOrigin)) {
|
||||||
|
MOZ_ASSERT(firstInitializationAttempt.Recorded());
|
||||||
return std::pair(std::move(directory), false);
|
return std::pair(std::move(directory), false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -6169,11 +6153,11 @@ QuotaManager::EnsurePersistentOriginIsInitialized(
|
||||||
mInitializedOrigins.AppendElement(aOriginMetadata.mOrigin);
|
mInitializedOrigins.AppendElement(aOriginMetadata.mOrigin);
|
||||||
|
|
||||||
return std::pair(std::move(directory), created);
|
return std::pair(std::move(directory), created);
|
||||||
}();
|
};
|
||||||
|
|
||||||
firstInitializationAttempt.MaybeRecord(res.isOk() ? NS_OK : res.inspectErr());
|
return ExecuteOriginInitialization(aOriginMetadata.mOrigin,
|
||||||
|
OriginInitialization::PersistentOrigin,
|
||||||
return res;
|
innerFunc());
|
||||||
}
|
}
|
||||||
|
|
||||||
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>
|
||||||
|
@ -6184,19 +6168,14 @@ QuotaManager::EnsureTemporaryOriginIsInitialized(
|
||||||
MOZ_DIAGNOSTIC_ASSERT(mStorageConnection);
|
MOZ_DIAGNOSTIC_ASSERT(mStorageConnection);
|
||||||
MOZ_DIAGNOSTIC_ASSERT(mTemporaryStorageInitialized);
|
MOZ_DIAGNOSTIC_ASSERT(mTemporaryStorageInitialized);
|
||||||
|
|
||||||
auto& originInitializationInfo =
|
const auto innerFunc = [&aPersistenceType, &aOriginMetadata, this]()
|
||||||
mInitializationInfo.MutableOriginInitializationInfoRef(
|
|
||||||
aOriginMetadata.mOrigin);
|
|
||||||
|
|
||||||
const auto firstInitializationAttempt =
|
|
||||||
originInitializationInfo.FirstInitializationAttempt(
|
|
||||||
OriginInitialization::TemporaryOrigin);
|
|
||||||
|
|
||||||
auto res = [&firstInitializationAttempt, &aPersistenceType, &aOriginMetadata,
|
|
||||||
this]()
|
|
||||||
-> mozilla::Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult> {
|
-> mozilla::Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult> {
|
||||||
const auto maybeExtraInfo =
|
const auto maybeExtraInfo =
|
||||||
firstInitializationAttempt.Pending()
|
mInitializationInfo
|
||||||
|
.MutableOriginInitializationInfoRef(aOriginMetadata.mOrigin,
|
||||||
|
CreateIfNonExistent{})
|
||||||
|
.FirstInitializationAttemptPending(
|
||||||
|
OriginInitialization::TemporaryOrigin)
|
||||||
? Some(ScopedLogExtraInfo{
|
? Some(ScopedLogExtraInfo{
|
||||||
ScopedLogExtraInfo::kTagContext,
|
ScopedLogExtraInfo::kTagContext,
|
||||||
"dom::quota::FirstOriginInitializationAttempt::TemporaryOrigin"_ns})
|
"dom::quota::FirstOriginInitializationAttempt::TemporaryOrigin"_ns})
|
||||||
|
@ -6228,27 +6207,22 @@ QuotaManager::EnsureTemporaryOriginIsInitialized(
|
||||||
// file in next session in LoadQuotaFromCache.
|
// file in next session in LoadQuotaFromCache.
|
||||||
|
|
||||||
return std::pair(std::move(directory), created);
|
return std::pair(std::move(directory), created);
|
||||||
}();
|
};
|
||||||
|
|
||||||
firstInitializationAttempt.MaybeRecord(res.isOk() ? NS_OK : res.inspectErr());
|
return ExecuteOriginInitialization(aOriginMetadata.mOrigin,
|
||||||
|
OriginInitialization::TemporaryOrigin,
|
||||||
return res;
|
innerFunc());
|
||||||
}
|
}
|
||||||
|
|
||||||
nsresult QuotaManager::EnsureTemporaryStorageIsInitialized() {
|
nsresult QuotaManager::EnsureTemporaryStorageIsInitialized() {
|
||||||
AssertIsOnIOThread();
|
AssertIsOnIOThread();
|
||||||
MOZ_DIAGNOSTIC_ASSERT(mStorageConnection);
|
MOZ_DIAGNOSTIC_ASSERT(mStorageConnection);
|
||||||
|
|
||||||
const auto firstInitializationAttempt =
|
const auto innerFunc = [this]() -> nsresult {
|
||||||
mInitializationInfo.FirstInitializationAttempt(
|
const auto firstInitializationAttempt =
|
||||||
Initialization::TemporaryStorage);
|
mInitializationInfo.FirstInitializationAttempt(
|
||||||
|
Initialization::TemporaryStorage);
|
||||||
|
|
||||||
if (mTemporaryStorageInitialized) {
|
|
||||||
MOZ_ASSERT(firstInitializationAttempt.Recorded());
|
|
||||||
return NS_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto rv = [&firstInitializationAttempt, this]() -> nsresult {
|
|
||||||
const auto maybeExtraInfo =
|
const auto maybeExtraInfo =
|
||||||
firstInitializationAttempt.Pending()
|
firstInitializationAttempt.Pending()
|
||||||
? Some(ScopedLogExtraInfo{
|
? Some(ScopedLogExtraInfo{
|
||||||
|
@ -6256,6 +6230,11 @@ nsresult QuotaManager::EnsureTemporaryStorageIsInitialized() {
|
||||||
"dom::quota::FirstInitializationAttempt::TemporaryStorage"_ns})
|
"dom::quota::FirstInitializationAttempt::TemporaryStorage"_ns})
|
||||||
: Nothing{};
|
: Nothing{};
|
||||||
|
|
||||||
|
if (mTemporaryStorageInitialized) {
|
||||||
|
MOZ_ASSERT(firstInitializationAttempt.Recorded());
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
QM_TRY_INSPECT(
|
QM_TRY_INSPECT(
|
||||||
const auto& storageDir,
|
const auto& storageDir,
|
||||||
ToResultGet<nsCOMPtr<nsIFile>>(MOZ_SELECT_OVERLOAD(do_CreateInstance),
|
ToResultGet<nsCOMPtr<nsIFile>>(MOZ_SELECT_OVERLOAD(do_CreateInstance),
|
||||||
|
@ -6283,7 +6262,7 @@ nsresult QuotaManager::EnsureTemporaryStorageIsInitialized() {
|
||||||
// limit calculation since available disk space is affected by existing data
|
// limit calculation since available disk space is affected by existing data
|
||||||
// stored in temporary storage. So we need to increase it by the temporary
|
// stored in temporary storage. So we need to increase it by the temporary
|
||||||
// storage size (that has been calculated in LoadQuota) before passing to
|
// storage size (that has been calculated in LoadQuota) before passing to
|
||||||
// GetTemporaryStorageLimit..
|
// GetTemporaryStorageLimit.
|
||||||
mTemporaryStorageLimit = GetTemporaryStorageLimit(
|
mTemporaryStorageLimit = GetTemporaryStorageLimit(
|
||||||
/* aAvailableSpaceBytes */ diskSpaceAvailable + mTemporaryStorageUsage);
|
/* aAvailableSpaceBytes */ diskSpaceAvailable + mTemporaryStorageUsage);
|
||||||
|
|
||||||
|
@ -6294,11 +6273,9 @@ nsresult QuotaManager::EnsureTemporaryStorageIsInitialized() {
|
||||||
}
|
}
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}();
|
};
|
||||||
|
|
||||||
firstInitializationAttempt.MaybeRecord(rv);
|
return ExecuteInitialization(Initialization::TemporaryStorage, innerFunc());
|
||||||
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void QuotaManager::ShutdownStorage() {
|
void QuotaManager::ShutdownStorage() {
|
||||||
|
@ -7103,6 +7080,22 @@ int64_t QuotaManager::GenerateDirectoryLockId() {
|
||||||
return directorylockId;
|
return directorylockId;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
nsresult QuotaManager::ExecuteInitialization(
|
||||||
|
const Initialization aInitialization, const nsresult aRv) {
|
||||||
|
return quota::ExecuteInitialization(mInitializationInfo, aInitialization,
|
||||||
|
aRv);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>
|
||||||
|
QuotaManager::ExecuteOriginInitialization(
|
||||||
|
const nsACString& aOrigin, const OriginInitialization aInitialization,
|
||||||
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>&& aResult) {
|
||||||
|
return quota::ExecuteInitialization(
|
||||||
|
mInitializationInfo.MutableOriginInitializationInfoRef(
|
||||||
|
aOrigin, CreateIfNonExistent{}),
|
||||||
|
aInitialization, std::move(aResult));
|
||||||
|
}
|
||||||
|
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
* Local class implementations
|
* Local class implementations
|
||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
|
|
|
@ -41,10 +41,6 @@ class FirstInitializationAttempts {
|
||||||
void Record(const nsresult aRv) const {
|
void Record(const nsresult aRv) const {
|
||||||
mOwner.RecordFirstInitializationAttempt(mInitialization, aRv);
|
mOwner.RecordFirstInitializationAttempt(mInitialization, aRv);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MaybeRecord(const nsresult aRv) const {
|
|
||||||
mOwner.MaybeRecordFirstInitializationAttempt(mInitialization, aRv);
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
FirstInitializationAttemptImpl FirstInitializationAttempt(
|
FirstInitializationAttemptImpl FirstInitializationAttempt(
|
||||||
|
@ -65,15 +61,6 @@ class FirstInitializationAttempts {
|
||||||
void RecordFirstInitializationAttempt(const Initialization aInitialization,
|
void RecordFirstInitializationAttempt(const Initialization aInitialization,
|
||||||
nsresult aRv);
|
nsresult aRv);
|
||||||
|
|
||||||
void MaybeRecordFirstInitializationAttempt(
|
|
||||||
const Initialization aInitialization, const nsresult aRv) {
|
|
||||||
if (FirstInitializationAttemptRecorded(aInitialization)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
RecordFirstInitializationAttempt(aInitialization, aRv);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ResetFirstInitializationAttempts() {
|
void ResetFirstInitializationAttempts() {
|
||||||
mFirstInitializationAttempts = Initialization::None;
|
mFirstInitializationAttempts = Initialization::None;
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,15 +22,6 @@ void FirstInitializationAttempts<Initialization, StringGenerator>::
|
||||||
const nsresult aRv) {
|
const nsresult aRv) {
|
||||||
MOZ_ASSERT(FirstInitializationAttemptPending(aInitialization));
|
MOZ_ASSERT(FirstInitializationAttemptPending(aInitialization));
|
||||||
|
|
||||||
// NS_ERROR_ABORT signals a non-fatal, recoverable problem during
|
|
||||||
// initialization. We do not want these kind of failures to count against our
|
|
||||||
// overall failure telemetry. Thus we just ignore this kind of failure and
|
|
||||||
// keep mFirstInitializationAttempts unflagged to stay ready to record a real
|
|
||||||
// failure on the next attempt.
|
|
||||||
if (aRv == NS_ERROR_ABORT) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mFirstInitializationAttempts |= aInitialization;
|
mFirstInitializationAttempts |= aInitialization;
|
||||||
|
|
||||||
if constexpr (!std::is_same_v<StringGenerator, Nothing>) {
|
if constexpr (!std::is_same_v<StringGenerator, Nothing>) {
|
||||||
|
|
|
@ -13,6 +13,10 @@
|
||||||
#include "nsStringFwd.h"
|
#include "nsStringFwd.h"
|
||||||
#include "nsTHashMap.h"
|
#include "nsTHashMap.h"
|
||||||
|
|
||||||
|
namespace mozilla {
|
||||||
|
struct CreateIfNonExistent;
|
||||||
|
}
|
||||||
|
|
||||||
namespace mozilla::dom::quota {
|
namespace mozilla::dom::quota {
|
||||||
|
|
||||||
enum class Initialization {
|
enum class Initialization {
|
||||||
|
@ -58,7 +62,7 @@ class InitializationInfo
|
||||||
|
|
||||||
public:
|
public:
|
||||||
OriginInitializationInfo& MutableOriginInitializationInfoRef(
|
OriginInitializationInfo& MutableOriginInitializationInfoRef(
|
||||||
const nsACString& aOrigin) {
|
const nsACString& aOrigin, const CreateIfNonExistent&) {
|
||||||
return mOriginInitializationInfos.LookupOrInsert(aOrigin);
|
return mOriginInitializationInfos.LookupOrInsert(aOrigin);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
# include "mozilla/Variant.h"
|
# include "mozilla/Variant.h"
|
||||||
#endif
|
#endif
|
||||||
#include "mozilla/dom/QMResult.h"
|
#include "mozilla/dom/QMResult.h"
|
||||||
|
#include "mozilla/dom/quota/FirstInitializationAttemptsImpl.h"
|
||||||
#include "mozilla/ipc/ProtocolUtils.h"
|
#include "mozilla/ipc/ProtocolUtils.h"
|
||||||
#include "nsCOMPtr.h"
|
#include "nsCOMPtr.h"
|
||||||
#include "nsDebug.h"
|
#include "nsDebug.h"
|
||||||
|
@ -983,6 +984,8 @@ namespace mozilla {
|
||||||
|
|
||||||
class LogModule;
|
class LogModule;
|
||||||
|
|
||||||
|
struct CreateIfNonExistent {};
|
||||||
|
|
||||||
struct NotOk {};
|
struct NotOk {};
|
||||||
|
|
||||||
// Allow MOZ_TRY/QM_TRY to handle `bool` values by wrapping them with OkIf.
|
// Allow MOZ_TRY/QM_TRY to handle `bool` values by wrapping them with OkIf.
|
||||||
|
@ -1537,6 +1540,50 @@ auto CallWithDelayedRetriesIfAccessDenied(Func&& aFunc, uint32_t aMaxRetries,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template <typename Initialization, typename StringGenerator>
|
||||||
|
nsresult ExecuteInitialization(
|
||||||
|
FirstInitializationAttempts<Initialization, StringGenerator>&
|
||||||
|
aFirstInitializationAttempts,
|
||||||
|
const Initialization aInitialization, const nsresult aRv) {
|
||||||
|
// NS_ERROR_ABORT signals a non-fatal, recoverable problem during
|
||||||
|
// initialization. We do not want these kind of failures to count against our
|
||||||
|
// overall first initialization attempt telemetry. Thus we just ignore this
|
||||||
|
// kind of failure and keep aFirstInitializationAttempts unflagged to stay
|
||||||
|
// ready to record a real success or failure on the next attempt.
|
||||||
|
if (aRv == NS_ERROR_ABORT) {
|
||||||
|
return aRv;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!aFirstInitializationAttempts.FirstInitializationAttemptRecorded(
|
||||||
|
aInitialization)) {
|
||||||
|
aFirstInitializationAttempts.RecordFirstInitializationAttempt(
|
||||||
|
aInitialization, aRv);
|
||||||
|
}
|
||||||
|
|
||||||
|
return aRv;
|
||||||
|
}
|
||||||
|
|
||||||
|
// XXX Get rid of this special overload.
|
||||||
|
template <typename Initialization, typename StringGenerator>
|
||||||
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult> ExecuteInitialization(
|
||||||
|
FirstInitializationAttempts<Initialization, StringGenerator>&
|
||||||
|
aFirstInitializationAttempts,
|
||||||
|
const Initialization aInitialization,
|
||||||
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>&& aResult) {
|
||||||
|
// See the comment above for the NS_ERROR_ABORT special case.
|
||||||
|
if (aResult.isErr() && aResult.inspectErr() == NS_ERROR_ABORT) {
|
||||||
|
return std::move(aResult);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!aFirstInitializationAttempts.FirstInitializationAttemptRecorded(
|
||||||
|
aInitialization)) {
|
||||||
|
aFirstInitializationAttempts.RecordFirstInitializationAttempt(
|
||||||
|
aInitialization, aResult.isOk() ? NS_OK : aResult.inspectErr());
|
||||||
|
}
|
||||||
|
|
||||||
|
return std::move(aResult);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace quota
|
} // namespace quota
|
||||||
} // namespace dom
|
} // namespace dom
|
||||||
} // namespace mozilla
|
} // namespace mozilla
|
||||||
|
|
|
@ -548,6 +548,14 @@ class QuotaManager final : public BackgroundThreadObject {
|
||||||
void MaybeRecordShutdownStep(Maybe<Client::Type> aClientType,
|
void MaybeRecordShutdownStep(Maybe<Client::Type> aClientType,
|
||||||
const nsACString& aStepDescription);
|
const nsACString& aStepDescription);
|
||||||
|
|
||||||
|
nsresult ExecuteInitialization(Initialization aInitialization, nsresult aRv);
|
||||||
|
|
||||||
|
// XXX Generalize this method.
|
||||||
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>
|
||||||
|
ExecuteOriginInitialization(
|
||||||
|
const nsACString& aOrigin, const OriginInitialization aInitialization,
|
||||||
|
Result<std::pair<nsCOMPtr<nsIFile>, bool>, nsresult>&& aResult);
|
||||||
|
|
||||||
template <typename Iterator>
|
template <typename Iterator>
|
||||||
static void MaybeInsertNonPersistedOriginInfos(
|
static void MaybeInsertNonPersistedOriginInfos(
|
||||||
Iterator aDest, const RefPtr<GroupInfo>& aTemporaryGroupInfo,
|
Iterator aDest, const RefPtr<GroupInfo>& aTemporaryGroupInfo,
|
||||||
|
|
Загрузка…
Ссылка в новой задаче