1
0
mirror of https://github.com/roytam1/UXP.git synced 2026-05-26 13:58:49 +00:00

Issue #2653 - Part 3: Remove support for packaged apps from asmjscache

This commit is contained in:
Moonchild
2024-11-18 13:58:43 +01:00
committed by roytam1
parent 0e6fa95840
commit 7f086f216c
10 changed files with 46 additions and 155 deletions
+24 -120
View File
@@ -30,7 +30,6 @@
#include "nsIAtom.h"
#include "nsIFile.h"
#include "nsIIPCBackgroundChildCreateCallback.h"
#include "nsIPermissionManager.h"
#include "nsIPrincipal.h"
#include "nsIRunnable.h"
#include "nsISimpleEnumerator.h"
@@ -443,11 +442,11 @@ public:
mPrincipalInfo(aPrincipalInfo),
mOpenMode(aOpenMode),
mWriteParams(aWriteParams),
mPersistence(quota::PERSISTENCE_TYPE_INVALID),
mState(eInitial),
mResult(JS::AsmJSCache_InternalError),
mIsApp(false),
mEnforcingQuota(true),
mDeleteReceived(false),
mActorDestroyed(false),
mOpened(false)
{
@@ -488,31 +487,6 @@ private:
MOZ_ASSERT(!IsOnOwningThread());
}
// This method is called on the owning thread when no cache entry was found
// to open. If we just tried a lookup in persistent storage then we might
// still get a hit in temporary storage (for an asm.js module that wasn't
// compiled at install-time).
void
CacheMiss()
{
AssertIsOnOwningThread();
MOZ_ASSERT(mState == eFailedToReadMetadata ||
mState == eWaitingToOpenCacheFileForRead);
MOZ_ASSERT(mOpenMode == eOpenForRead);
if (mPersistence == quota::PERSISTENCE_TYPE_TEMPORARY) {
Fail();
return;
}
// Try again with a clean slate. InitOnMainThread will see that mPersistence
// is initialized and switch to temporary storage.
MOZ_ASSERT(mPersistence == quota::PERSISTENCE_TYPE_PERSISTENT);
FinishOnOwningThread();
mState = eInitial;
NS_DispatchToMainThread(this);
}
// This method is called on the owning thread when the JS engine is finished
// reading/writing the cache entry.
void
@@ -542,7 +516,7 @@ private:
FinishOnOwningThread();
if (!mActorDestroyed) {
if (!mDeleteReceived && !mActorDestroyed) {
Unused << Send__delete__(this, mResult);
}
}
@@ -561,9 +535,6 @@ private:
MOZ_ALWAYS_SUCCEEDS(mOwningThread->Dispatch(this, NS_DISPATCH_NORMAL));
}
void
InitPersistenceType();
nsresult
InitOnMainThread();
@@ -615,6 +586,10 @@ private:
AssertIsOnOwningThread();
MOZ_ASSERT(mState != eFinished);
MOZ_ASSERT(!mDeleteReceived);
mDeleteReceived = true;
if (mOpened) {
Close();
} else {
@@ -666,23 +641,12 @@ private:
return true;
}
bool
RecvCacheMiss() override
{
AssertIsOnOwningThread();
CacheMiss();
return true;
}
nsCOMPtr<nsIEventTarget> mOwningThread;
const PrincipalInfo mPrincipalInfo;
const OpenMode mOpenMode;
const WriteParams mWriteParams;
// State initialized during eInitial:
quota::PersistenceType mPersistence;
nsCString mSuffix;
nsCString mGroup;
nsCString mOrigin;
@@ -702,7 +666,6 @@ private:
eWaitingToOpenDirectory, // Waiting to open directory
eWaitingToOpenMetadata, // Waiting to be called back from OpenDirectory
eReadyToReadMetadata, // Waiting to read the metadata file on the IO thread
eFailedToReadMetadata, // Waiting to be dispatched to owning thread after fail
eSendingMetadataForRead, // Waiting to send OnOpenMetadataForRead
eWaitingToOpenCacheFileForRead, // Waiting to hear back from child
eReadyToOpenCacheFileForRead, // Waiting to open cache file for read
@@ -716,56 +679,11 @@ private:
bool mIsApp;
bool mEnforcingQuota;
bool mDeleteReceived;
bool mActorDestroyed;
bool mOpened;
};
void
ParentRunnable::InitPersistenceType()
{
MOZ_ASSERT(NS_IsMainThread());
MOZ_ASSERT(mState == eInitial);
if (mOpenMode == eOpenForWrite) {
MOZ_ASSERT(mPersistence == quota::PERSISTENCE_TYPE_INVALID);
// If we are performing install-time caching of an app, we'd like to store
// the cache entry in persistent storage so the entry is never evicted,
// but we need to check that quota is not enforced for the app.
// That justifies us in skipping all quota checks when storing the cache
// entry and avoids all the issues around the persistent quota prompt.
// If quota is enforced for the app, then we can still cache in temporary
// for a likely good first-run experience.
MOZ_ASSERT_IF(mWriteParams.mInstalled, mIsApp);
if (mWriteParams.mInstalled &&
!QuotaManager::IsQuotaEnforced(quota::PERSISTENCE_TYPE_PERSISTENT,
mOrigin, mIsApp)) {
mPersistence = quota::PERSISTENCE_TYPE_PERSISTENT;
} else {
mPersistence = quota::PERSISTENCE_TYPE_TEMPORARY;
}
return;
}
// For the reasons described above, apps may have cache entries in both
// persistent and temporary storage. At lookup time we don't know how and
// where the given script was cached, so start the search in persistent
// storage and, if that fails, search in temporary storage. (Non-apps can
// only be stored in temporary storage.)
MOZ_ASSERT_IF(mPersistence != quota::PERSISTENCE_TYPE_INVALID,
mIsApp && mPersistence == quota::PERSISTENCE_TYPE_PERSISTENT);
if (mPersistence == quota::PERSISTENCE_TYPE_INVALID && mIsApp) {
mPersistence = quota::PERSISTENCE_TYPE_PERSISTENT;
} else {
mPersistence = quota::PERSISTENCE_TYPE_TEMPORARY;
}
}
nsresult
ParentRunnable::InitOnMainThread()
{
@@ -784,10 +702,8 @@ ParentRunnable::InitOnMainThread()
&mOrigin, &mIsApp);
NS_ENSURE_SUCCESS(rv, rv);
InitPersistenceType();
mEnforcingQuota =
QuotaManager::IsQuotaEnforced(mPersistence, mOrigin, mIsApp);
QuotaManager::IsQuotaEnforced(quota::PERSISTENCE_TYPE_TEMPORARY, mOrigin, mIsApp);
return NS_OK;
}
@@ -803,7 +719,7 @@ ParentRunnable::OpenDirectory()
mState = eWaitingToOpenMetadata;
// XXX The exclusive lock shouldn't be needed for read operations.
QuotaManager::Get()->OpenDirectory(mPersistence,
QuotaManager::Get()->OpenDirectory(quota::PERSISTENCE_TYPE_TEMPORARY,
mGroup,
mOrigin,
mIsApp,
@@ -822,8 +738,12 @@ ParentRunnable::ReadMetadata()
MOZ_ASSERT(qm, "We are on the QuotaManager's IO thread");
nsresult rv =
qm->EnsureOriginIsInitialized(mPersistence, mSuffix, mGroup, mOrigin,
mIsApp, getter_AddRefs(mDirectory));
qm->EnsureOriginIsInitialized(quota::PERSISTENCE_TYPE_TEMPORARY,
mSuffix,
mGroup,
mOrigin,
mIsApp,
getter_AddRefs(mDirectory));
if (NS_WARN_IF(NS_FAILED(rv))) {
mResult = JS::AsmJSCache_StorageInitFailure;
return rv;
@@ -898,7 +818,7 @@ ParentRunnable::OpenCacheFileForWrite()
// Create the QuotaObject before all file IO and keep it alive until caching
// completes to get maximum assertion coverage in QuotaManager against
// concurrent removal, etc.
mQuotaObject = qm->GetQuotaObject(mPersistence, mGroup, mOrigin, file);
mQuotaObject = qm->GetQuotaObject(quota::PERSISTENCE_TYPE_TEMPORARY, mGroup, mOrigin, file);
NS_ENSURE_STATE(mQuotaObject);
if (!mQuotaObject->MaybeUpdateSize(mWriteParams.mSize,
@@ -952,7 +872,7 @@ ParentRunnable::OpenCacheFileForRead()
// Even though it's not strictly necessary, create the QuotaObject before
// all file IO and keep it alive until caching completes to get maximum
// assertion coverage in QuotaManager against concurrent removal, etc.
mQuotaObject = qm->GetQuotaObject(mPersistence, mGroup, mOrigin, file);
mQuotaObject = qm->GetQuotaObject(quota::PERSISTENCE_TYPE_TEMPORARY, mGroup, mOrigin, file);
NS_ENSURE_STATE(mQuotaObject);
}
@@ -1058,8 +978,7 @@ ParentRunnable::Run()
rv = ReadMetadata();
if (NS_FAILED(rv)) {
mState = eFailedToReadMetadata;
MOZ_ALWAYS_SUCCEEDS(mOwningThread->Dispatch(this, NS_DISPATCH_NORMAL));
FailOnNonOwningThread();
return NS_OK;
}
@@ -1081,18 +1000,6 @@ ParentRunnable::Run()
return NS_OK;
}
case eFailedToReadMetadata: {
AssertIsOnOwningThread();
if (mOpenMode == eOpenForRead) {
CacheMiss();
return NS_OK;
}
Fail();
return NS_OK;
}
case eSendingMetadataForRead: {
AssertIsOnOwningThread();
MOZ_ASSERT(mOpenMode == eOpenForRead);
@@ -1404,11 +1311,13 @@ private:
MOZ_ASSERT(mState == eOpening);
uint32_t moduleIndex;
if (FindHashMatch(aMetadata, mReadParams, &moduleIndex)) {
return SendSelectCacheFileToRead(moduleIndex);
if (!FindHashMatch(aMetadata, mReadParams, &moduleIndex)) {
Fail(JS::AsmJSCache_InternalError);
Send__delete__(this, JS::AsmJSCache_InternalError);
return true;
}
return SendCacheMiss();
return SendSelectCacheFileToRead(moduleIndex);
}
bool
@@ -1760,7 +1669,6 @@ CloseEntryForRead(size_t aSize,
JS::AsmJSCacheResult
OpenEntryForWrite(nsIPrincipal* aPrincipal,
bool aInstalled,
const char16_t* aBegin,
const char16_t* aEnd,
size_t aSize,
@@ -1777,7 +1685,6 @@ OpenEntryForWrite(nsIPrincipal* aPrincipal,
static_assert(sNumFastHashChars < sMinCachedModuleLength, "HashString safe");
WriteParams writeParams;
writeParams.mInstalled = aInstalled;
writeParams.mSize = aSize;
writeParams.mFastHash = HashString(aBegin, sNumFastHashChars);
writeParams.mNumChars = aEnd - aBegin;
@@ -2043,7 +1950,6 @@ ParamTraits<WriteParams>::Write(Message* aMsg, const paramType& aParam)
WriteParam(aMsg, aParam.mFastHash);
WriteParam(aMsg, aParam.mNumChars);
WriteParam(aMsg, aParam.mFullHash);
WriteParam(aMsg, aParam.mInstalled);
}
bool
@@ -2053,8 +1959,7 @@ ParamTraits<WriteParams>::Read(const Message* aMsg, PickleIterator* aIter,
return ReadParam(aMsg, aIter, &aResult->mSize) &&
ReadParam(aMsg, aIter, &aResult->mFastHash) &&
ReadParam(aMsg, aIter, &aResult->mNumChars) &&
ReadParam(aMsg, aIter, &aResult->mFullHash) &&
ReadParam(aMsg, aIter, &aResult->mInstalled);
ReadParam(aMsg, aIter, &aResult->mFullHash);
}
void
@@ -2064,7 +1969,6 @@ ParamTraits<WriteParams>::Log(const paramType& aParam, std::wstring* aLog)
LogParam(aParam.mFastHash, aLog);
LogParam(aParam.mNumChars, aLog);
LogParam(aParam.mFullHash, aLog);
LogParam(aParam.mInstalled, aLog);
}
} // namespace IPC
+6 -9
View File
@@ -72,14 +72,12 @@ struct WriteParams
int64_t mFastHash;
int64_t mNumChars;
int64_t mFullHash;
bool mInstalled;
WriteParams()
: mSize(0),
mFastHash(0),
mNumChars(0),
mFullHash(0),
mInstalled(false)
: mSize(0)
, mFastHash(0)
, mNumChars(0)
, mFullHash(0)
{ }
};
@@ -90,8 +88,8 @@ struct ReadParams
const char16_t* mLimit;
ReadParams()
: mBegin(nullptr),
mLimit(nullptr)
: mBegin(nullptr)
, mLimit(nullptr)
{ }
};
@@ -120,7 +118,6 @@ CloseEntryForRead(size_t aSize,
intptr_t aHandle);
JS::AsmJSCacheResult
OpenEntryForWrite(nsIPrincipal* aPrincipal,
bool aInstalled,
const char16_t* aBegin,
const char16_t* aEnd,
size_t aSize,
-1
View File
@@ -22,7 +22,6 @@ child:
async OnOpenMetadataForRead(Metadata metadata);
parent:
async SelectCacheFileToRead(uint32_t moduleIndex);
async CacheMiss();
child:
// Once the cache file has been opened, the child is notified and sent an
+1 -3
View File
@@ -2265,7 +2265,6 @@ AsmJSCacheOpenEntryForRead(JS::Handle<JSObject*> aGlobal,
static JS::AsmJSCacheResult
AsmJSCacheOpenEntryForWrite(JS::Handle<JSObject*> aGlobal,
bool aInstalled,
const char16_t* aBegin,
const char16_t* aEnd,
size_t aSize,
@@ -2274,8 +2273,7 @@ AsmJSCacheOpenEntryForWrite(JS::Handle<JSObject*> aGlobal,
{
nsIPrincipal* principal =
nsJSPrincipals::get(JS_GetCompartmentPrincipals(js::GetObjectCompartment(aGlobal)));
return asmjscache::OpenEntryForWrite(principal, aInstalled, aBegin, aEnd,
aSize, aMemory, aHandle);
return asmjscache::OpenEntryForWrite(principal, aBegin, aEnd, aSize, aMemory, aHandle);
}
class AsyncTaskRunnable final : public Runnable
+1 -3
View File
@@ -677,7 +677,6 @@ AsmJSCacheOpenEntryForRead(JS::Handle<JSObject*> aGlobal,
static JS::AsmJSCacheResult
AsmJSCacheOpenEntryForWrite(JS::Handle<JSObject*> aGlobal,
bool aInstalled,
const char16_t* aBegin,
const char16_t* aEnd,
size_t aSize,
@@ -689,8 +688,7 @@ AsmJSCacheOpenEntryForWrite(JS::Handle<JSObject*> aGlobal,
return JS::AsmJSCache_InternalError;
}
return asmjscache::OpenEntryForWrite(principal, aInstalled, aBegin, aEnd,
aSize, aMemory, aHandle);
return asmjscache::OpenEntryForWrite(principal, aBegin, aEnd, aSize, aMemory, aHandle);
}
class AsyncTaskWorkerHolder final : public WorkerHolder
-1
View File
@@ -3826,7 +3826,6 @@ JS::TransitiveCompileOptions::copyPODTransitiveOptions(const TransitiveCompileOp
asmJSOption = rhs.asmJSOption;
throwOnAsmJSValidationFailureOption = rhs.throwOnAsmJSValidationFailureOption;
forceAsync = rhs.forceAsync;
installedFile = rhs.installedFile;
sourceIsLazy = rhs.sourceIsLazy;
introductionType = rhs.introductionType;
introductionLineno = rhs.introductionLineno;
+6 -11
View File
@@ -3821,7 +3821,6 @@ class JS_FRIEND_API(TransitiveCompileOptions)
asmJSOption(AsmJSOption::Disabled),
throwOnAsmJSValidationFailureOption(false),
forceAsync(false),
installedFile(false),
sourceIsLazy(false),
introductionType(nullptr),
introductionLineno(0),
@@ -3856,7 +3855,6 @@ class JS_FRIEND_API(TransitiveCompileOptions)
AsmJSOption asmJSOption;
bool throwOnAsmJSValidationFailureOption;
bool forceAsync;
bool installedFile; // 'true' iff pre-compiling js file in packaged app
bool sourceIsLazy;
// |introductionType| is a statically allocated C string:
@@ -6300,17 +6298,14 @@ enum AsmJSCacheResult
* outparams. If the callback returns 'true', the JS engine guarantees a call
* to CloseAsmJSCacheEntryForWriteOp passing the same base address, size and
* handle.
*
* If 'installed' is true, then the cache entry is associated with a permanently
* installed JS file (e.g., in a packaged webapp). This information allows the
* embedding to store the cache entry in a installed location associated with
* the principal of 'global' where it will not be evicted until the associated
* installed JS file is removed.
*/
typedef AsmJSCacheResult
(* OpenAsmJSCacheEntryForWriteOp)(HandleObject global, bool installed,
const char16_t* begin, const char16_t* end,
size_t size, uint8_t** memory, intptr_t* handle);
(* OpenAsmJSCacheEntryForWriteOp)(HandleObject global,
const char16_t* begin,
const char16_t* end,
size_t size,
uint8_t** memory,
intptr_t* handle);
typedef void
(* CloseAsmJSCacheEntryForWriteOp)(size_t size, uint8_t* memory, intptr_t handle);
+6 -3
View File
@@ -7215,9 +7215,12 @@ ShellCloseAsmJSCacheEntryForRead(size_t serializedSize, const uint8_t* memory, i
}
static JS::AsmJSCacheResult
ShellOpenAsmJSCacheEntryForWrite(HandleObject global, bool installed,
const char16_t* begin, const char16_t* end,
size_t serializedSize, uint8_t** memoryOut, intptr_t* handleOut)
ShellOpenAsmJSCacheEntryForWrite(HandleObject global,
const char16_t* begin,
const char16_t* end,
size_t serializedSize,
uint8_t** memoryOut,
intptr_t* handleOut)
{
if (!jsCachingEnabled || !jsCacheAsmJSPath)
return JS::AsmJSCache_Disabled_ShellFlags;
+2 -3
View File
@@ -1,7 +1,7 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* Copyright 2014 Mozilla Foundation
* Copyright 2022, 2023 Moonchild Productions
* Copyright 2022-2024 Moonchild Productions
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -6700,11 +6700,10 @@ StoreAsmJSModuleInCache(AsmJSParser& parser, Module& module, ExclusiveContext* c
const char16_t* begin = parser.tokenStream.rawCharPtrAt(ModuleChars::beginOffset(parser));
const char16_t* end = parser.tokenStream.rawCharPtrAt(ModuleChars::endOffset(parser));
bool installed = parser.options().installedFile;
ScopedCacheEntryOpenedForWrite entry(cx, serializedSize);
JS::AsmJSCacheResult openResult =
open(cx->global(), installed, begin, end, serializedSize, &entry.memory, &entry.handle);
open(cx->global(), begin, end, serializedSize, &entry.memory, &entry.handle);
if (openResult != JS::AsmJSCache_Success)
return openResult;
@@ -848,7 +848,6 @@ ScriptPrecompiler::OnStreamComplete(nsIIncrementalStreamLoader* aLoader,
JS::CompileOptions options(cx, JSVERSION_DEFAULT);
options.forceAsync = true;
options.installedFile = true;
nsCOMPtr<nsIURI> uri;
mChannel->GetURI(getter_AddRefs(uri));