Bug 1627892 - Make InternalRequest derive from SafeRefCounted. r=dom-workers-and-storage-reviewers,perry

Differential Revision: https://phabricator.services.mozilla.com/D69958
This commit is contained in:
Simon Giesecke 2020-05-11 12:10:53 +00:00
parent c4c6f0c42c
commit 32076b1063
22 changed files with 157 additions and 145 deletions

View File

@ -124,8 +124,9 @@ AutoChildOpArgs::~AutoChildOpArgs() {
mStreamCleanupList.Clear();
}
void AutoChildOpArgs::Add(InternalRequest* aRequest, BodyAction aBodyAction,
SchemeAction aSchemeAction, ErrorResult& aRv) {
void AutoChildOpArgs::Add(const InternalRequest& aRequest,
BodyAction aBodyAction, SchemeAction aSchemeAction,
ErrorResult& aRv) {
MOZ_DIAGNOSTIC_ASSERT(!mSent);
switch (mOpArgs.type()) {
@ -172,10 +173,8 @@ void AutoChildOpArgs::Add(InternalRequest* aRequest, BodyAction aBodyAction,
namespace {
bool MatchInPutList(InternalRequest* aRequest,
bool MatchInPutList(const InternalRequest& aRequest,
const nsTArray<CacheRequestResponse>& aPutList) {
MOZ_DIAGNOSTIC_ASSERT(aRequest);
// This method implements the SW spec QueryCache algorithm against an
// in memory array of Request/Response objects. This essentially the
// same algorithm that is implemented in DBSchema.cpp. Unfortunately
@ -186,19 +185,19 @@ bool MatchInPutList(InternalRequest* aRequest,
// Cache should only call into here with a GET or HEAD.
#ifdef DEBUG
nsAutoCString method;
aRequest->GetMethod(method);
aRequest.GetMethod(method);
MOZ_ASSERT(method.LowerCaseEqualsLiteral("get") ||
method.LowerCaseEqualsLiteral("head"));
#endif
RefPtr<InternalHeaders> requestHeaders = aRequest->Headers();
RefPtr<InternalHeaders> requestHeaders = aRequest.Headers();
for (uint32_t i = 0; i < aPutList.Length(); ++i) {
const CacheRequest& cachedRequest = aPutList[i].request();
const CacheResponse& cachedResponse = aPutList[i].response();
nsAutoCString url;
aRequest->GetURL(url);
aRequest.GetURL(url);
nsAutoCString requestUrl(cachedRequest.urlWithoutQuery());
requestUrl.Append(cachedRequest.urlQuery());
@ -263,7 +262,7 @@ bool MatchInPutList(InternalRequest* aRequest,
} // namespace
void AutoChildOpArgs::Add(JSContext* aCx, InternalRequest* aRequest,
void AutoChildOpArgs::Add(JSContext* aCx, const InternalRequest& aRequest,
BodyAction aBodyAction, SchemeAction aSchemeAction,
Response& aResponse, ErrorResult& aRv) {
MOZ_DIAGNOSTIC_ASSERT(!mSent);

View File

@ -54,10 +54,11 @@ class MOZ_STACK_CLASS AutoChildOpArgs final {
uint32_t aEntryCount);
~AutoChildOpArgs();
void Add(InternalRequest* aRequest, BodyAction aBodyAction,
void Add(const InternalRequest& aRequest, BodyAction aBodyAction,
SchemeAction aSchemeAction, ErrorResult& aRv);
void Add(JSContext* aCx, InternalRequest* aRequest, BodyAction aBodyAction,
SchemeAction aSchemeAction, Response& aResponse, ErrorResult& aRv);
void Add(JSContext* aCx, const InternalRequest& aRequest,
BodyAction aBodyAction, SchemeAction aSchemeAction,
Response& aResponse, ErrorResult& aRv);
const CacheOpArgs& SendAsOpArgs();

25
dom/cache/Cache.cpp vendored
View File

@ -254,7 +254,7 @@ already_AddRefed<Promise> Cache::Match(JSContext* aCx,
CacheChild::AutoLock actorLock(*mActor);
RefPtr<InternalRequest> ir =
SafeRefPtr<InternalRequest> ir =
ToInternalRequest(aCx, aRequest, IgnoreBody, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
@ -266,7 +266,7 @@ already_AddRefed<Promise> Cache::Match(JSContext* aCx,
AutoChildOpArgs args(
this, CacheMatchArgs(CacheRequest(), params, GetOpenMode()), 1);
args.Add(ir, IgnoreBody, IgnoreInvalidScheme, aRv);
args.Add(*ir, IgnoreBody, IgnoreInvalidScheme, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
@ -291,13 +291,13 @@ already_AddRefed<Promise> Cache::MatchAll(
CacheMatchAllArgs(Nothing(), params, GetOpenMode()), 1);
if (aRequest.WasPassed()) {
RefPtr<InternalRequest> ir =
SafeRefPtr<InternalRequest> ir =
ToInternalRequest(aCx, aRequest.Value(), IgnoreBody, aRv);
if (aRv.Failed()) {
return nullptr;
}
args.Add(ir, IgnoreBody, IgnoreInvalidScheme, aRv);
args.Add(*ir, IgnoreBody, IgnoreInvalidScheme, aRv);
if (aRv.Failed()) {
return nullptr;
}
@ -404,14 +404,15 @@ already_AddRefed<Promise> Cache::Put(JSContext* aCx,
return nullptr;
}
RefPtr<InternalRequest> ir = ToInternalRequest(aCx, aRequest, ReadBody, aRv);
SafeRefPtr<InternalRequest> ir =
ToInternalRequest(aCx, aRequest, ReadBody, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
AutoChildOpArgs args(this, CachePutAllArgs(), 1);
args.Add(aCx, ir, ReadBody, TypeErrorOnInvalidScheme, aResponse, aRv);
args.Add(aCx, *ir, ReadBody, TypeErrorOnInvalidScheme, aResponse, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
@ -430,7 +431,7 @@ already_AddRefed<Promise> Cache::Delete(JSContext* aCx,
CacheChild::AutoLock actorLock(*mActor);
RefPtr<InternalRequest> ir =
SafeRefPtr<InternalRequest> ir =
ToInternalRequest(aCx, aRequest, IgnoreBody, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
@ -441,7 +442,7 @@ already_AddRefed<Promise> Cache::Delete(JSContext* aCx,
AutoChildOpArgs args(this, CacheDeleteArgs(CacheRequest(), params), 1);
args.Add(ir, IgnoreBody, IgnoreInvalidScheme, aRv);
args.Add(*ir, IgnoreBody, IgnoreInvalidScheme, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
@ -466,13 +467,13 @@ already_AddRefed<Promise> Cache::Keys(
1);
if (aRequest.WasPassed()) {
RefPtr<InternalRequest> ir =
SafeRefPtr<InternalRequest> ir =
ToInternalRequest(aCx, aRequest.Value(), IgnoreBody, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
args.Add(ir, IgnoreBody, IgnoreInvalidScheme, aRv);
args.Add(*ir, IgnoreBody, IgnoreInvalidScheme, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
}
@ -598,8 +599,8 @@ already_AddRefed<Promise> Cache::PutAll(
AutoChildOpArgs args(this, CachePutAllArgs(), aRequestList.Length());
for (uint32_t i = 0; i < aRequestList.Length(); ++i) {
RefPtr<InternalRequest> ir = aRequestList[i]->GetInternalRequest();
args.Add(aCx, ir, ReadBody, TypeErrorOnInvalidScheme, *aResponseList[i],
SafeRefPtr<InternalRequest> ir = aRequestList[i]->GetInternalRequest();
args.Add(aCx, *ir, ReadBody, TypeErrorOnInvalidScheme, *aResponseList[i],
aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;

View File

@ -63,7 +63,7 @@ struct CacheStorage::Entry final {
CacheOpArgs mArgs;
// We cannot add the requests until after the actor is present. So store
// the request data separately for now.
RefPtr<InternalRequest> mRequest;
SafeRefPtr<InternalRequest> mRequest;
};
namespace {
@ -319,7 +319,7 @@ already_AddRefed<Promise> CacheStorage::Match(
return nullptr;
}
RefPtr<InternalRequest> request =
SafeRefPtr<InternalRequest> request =
ToInternalRequest(aCx, aRequest, IgnoreBody, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return nullptr;
@ -336,7 +336,7 @@ already_AddRefed<Promise> CacheStorage::Match(
auto entry = MakeUnique<Entry>();
entry->mPromise = promise;
entry->mArgs = StorageMatchArgs(CacheRequest(), params, GetOpenMode());
entry->mRequest = request;
entry->mRequest = std::move(request);
RunRequest(std::move(entry));
@ -547,7 +547,7 @@ void CacheStorage::RunRequest(UniquePtr<Entry> aEntry) {
if (aEntry->mRequest) {
ErrorResult rv;
args.Add(aEntry->mRequest, IgnoreBody, IgnoreInvalidScheme, rv);
args.Add(*aEntry->mRequest, IgnoreBody, IgnoreInvalidScheme, rv);
if (NS_WARN_IF(rv.Failed())) {
aEntry->mPromise->MaybeReject(std::move(rv));
return;

View File

@ -74,7 +74,7 @@ void ToHeadersEntryList(nsTArray<HeadersEntry>& aOut,
} // namespace
already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
SafeRefPtr<InternalRequest> TypeUtils::ToInternalRequest(
JSContext* aCx, const RequestOrUSVString& aIn, BodyAction aBodyAction,
ErrorResult& aRv) {
if (aIn.IsRequest()) {
@ -93,7 +93,7 @@ already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
return ToInternalRequest(aIn.GetAsUSVString(), aRv);
}
already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
SafeRefPtr<InternalRequest> TypeUtils::ToInternalRequest(
JSContext* aCx, const OwningRequestOrUSVString& aIn, BodyAction aBodyAction,
ErrorResult& aRv) {
if (aIn.IsRequest()) {
@ -113,12 +113,11 @@ already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
}
void TypeUtils::ToCacheRequest(
CacheRequest& aOut, InternalRequest* aIn, BodyAction aBodyAction,
CacheRequest& aOut, const InternalRequest& aIn, BodyAction aBodyAction,
SchemeAction aSchemeAction,
nsTArray<UniquePtr<AutoIPCStream>>& aStreamCleanupList, ErrorResult& aRv) {
MOZ_DIAGNOSTIC_ASSERT(aIn);
aIn->GetMethod(aOut.method());
nsCString url(aIn->GetURLWithoutFragment());
aIn.GetMethod(aOut.method());
nsCString url(aIn.GetURLWithoutFragment());
bool schemeValid;
ProcessURL(url, &schemeValid, &aOut.urlWithoutQuery(), &aOut.urlQuery(), aRv);
if (aRv.Failed()) {
@ -130,21 +129,21 @@ void TypeUtils::ToCacheRequest(
return;
}
}
aOut.urlFragment() = aIn->GetFragment();
aOut.urlFragment() = aIn.GetFragment();
aIn->GetReferrer(aOut.referrer());
aOut.referrerPolicy() = aIn->ReferrerPolicy_();
RefPtr<InternalHeaders> headers = aIn->Headers();
aIn.GetReferrer(aOut.referrer());
aOut.referrerPolicy() = aIn.ReferrerPolicy_();
RefPtr<InternalHeaders> headers = aIn.Headers();
MOZ_DIAGNOSTIC_ASSERT(headers);
ToHeadersEntryList(aOut.headers(), headers);
aOut.headersGuard() = headers->Guard();
aOut.mode() = aIn->Mode();
aOut.credentials() = aIn->GetCredentialsMode();
aOut.contentPolicyType() = aIn->ContentPolicyType();
aOut.requestCache() = aIn->GetCacheMode();
aOut.requestRedirect() = aIn->GetRedirectMode();
aOut.mode() = aIn.Mode();
aOut.credentials() = aIn.GetCredentialsMode();
aOut.contentPolicyType() = aIn.ContentPolicyType();
aOut.requestCache() = aIn.GetCacheMode();
aOut.requestRedirect() = aIn.GetRedirectMode();
aOut.integrity() = aIn->GetIntegrity();
aOut.integrity() = aIn.GetIntegrity();
if (aBodyAction == IgnoreBody) {
aOut.body() = Nothing();
@ -154,7 +153,7 @@ void TypeUtils::ToCacheRequest(
// BodyUsed flag is checked and set previously in ToInternalRequest()
nsCOMPtr<nsIInputStream> stream;
aIn->GetBody(getter_AddRefs(stream));
aIn.GetBody(getter_AddRefs(stream));
SerializeCacheStream(stream, &aOut.body(), aStreamCleanupList, aRv);
if (NS_WARN_IF(aRv.Failed())) {
return;
@ -304,12 +303,12 @@ already_AddRefed<Response> TypeUtils::ToResponse(const CacheResponse& aIn) {
RefPtr<Response> ref = new Response(GetGlobalObject(), ir, nullptr);
return ref.forget();
}
already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
SafeRefPtr<InternalRequest> TypeUtils::ToInternalRequest(
const CacheRequest& aIn) {
nsAutoCString url(aIn.urlWithoutQuery());
url.Append(aIn.urlQuery());
RefPtr<InternalRequest> internalRequest =
new InternalRequest(url, aIn.urlFragment());
auto internalRequest =
MakeSafeRefPtr<InternalRequest>(url, aIn.urlFragment());
internalRequest->SetMethod(aIn.method());
internalRequest->SetReferrer(aIn.referrer());
internalRequest->SetReferrerPolicy(aIn.referrerPolicy());
@ -336,13 +335,12 @@ already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
internalRequest->SetBody(stream, -1);
return internalRequest.forget();
return internalRequest;
}
already_AddRefed<Request> TypeUtils::ToRequest(const CacheRequest& aIn) {
RefPtr<InternalRequest> internalRequest = ToInternalRequest(aIn);
RefPtr<Request> request =
new Request(GetGlobalObject(), internalRequest, nullptr);
new Request(GetGlobalObject(), ToInternalRequest(aIn), nullptr);
return request.forget();
}
@ -447,8 +445,8 @@ void TypeUtils::CheckAndSetBodyUsed(JSContext* aCx, Request* aRequest,
}
}
already_AddRefed<InternalRequest> TypeUtils::ToInternalRequest(
const nsAString& aIn, ErrorResult& aRv) {
SafeRefPtr<InternalRequest> TypeUtils::ToInternalRequest(const nsAString& aIn,
ErrorResult& aRv) {
RequestOrUSVString requestOrString;
requestOrString.SetAsUSVString().ShareOrDependUpon(aIn);

18
dom/cache/TypeUtils.h vendored
View File

@ -10,6 +10,7 @@
#include "mozilla/Attributes.h"
#include "mozilla/dom/BindingUtils.h"
#include "mozilla/dom/InternalHeaders.h"
#include "mozilla/dom/SafeRefPtr.h"
#include "nsError.h"
class nsIGlobalObject;
@ -61,16 +62,17 @@ class TypeUtils {
// GetIPCManager().
virtual mozilla::ipc::PBackgroundChild* GetIPCManager() = 0;
already_AddRefed<InternalRequest> ToInternalRequest(
JSContext* aCx, const RequestOrUSVString& aIn, BodyAction aBodyAction,
ErrorResult& aRv);
SafeRefPtr<InternalRequest> ToInternalRequest(JSContext* aCx,
const RequestOrUSVString& aIn,
BodyAction aBodyAction,
ErrorResult& aRv);
already_AddRefed<InternalRequest> ToInternalRequest(
SafeRefPtr<InternalRequest> ToInternalRequest(
JSContext* aCx, const OwningRequestOrUSVString& aIn,
BodyAction aBodyAction, ErrorResult& aRv);
void ToCacheRequest(
CacheRequest& aOut, InternalRequest* aIn, BodyAction aBodyAction,
CacheRequest& aOut, const InternalRequest& aIn, BodyAction aBodyAction,
SchemeAction aSchemeAction,
nsTArray<UniquePtr<mozilla::ipc::AutoIPCStream>>& aStreamCleanupList,
ErrorResult& aRv);
@ -87,7 +89,7 @@ class TypeUtils {
already_AddRefed<Response> ToResponse(const CacheResponse& aIn);
already_AddRefed<InternalRequest> ToInternalRequest(const CacheRequest& aIn);
SafeRefPtr<InternalRequest> ToInternalRequest(const CacheRequest& aIn);
already_AddRefed<Request> ToRequest(const CacheRequest& aIn);
@ -118,8 +120,8 @@ class TypeUtils {
void CheckAndSetBodyUsed(JSContext* aCx, Request* aRequest,
BodyAction aBodyAction, ErrorResult& aRv);
already_AddRefed<InternalRequest> ToInternalRequest(const nsAString& aIn,
ErrorResult& aRv);
SafeRefPtr<InternalRequest> ToInternalRequest(const nsAString& aIn,
ErrorResult& aRv);
void SerializeCacheStream(
nsIInputStream* aStream, Maybe<CacheReadStream>* aStreamOut,

View File

@ -354,7 +354,7 @@ class MainThreadFetchRunnable : public Runnable {
const ClientInfo mClientInfo;
const Maybe<ServiceWorkerDescriptor> mController;
nsCOMPtr<nsICSPEventListener> mCSPEventListener;
RefPtr<InternalRequest> mRequest;
SafeRefPtr<InternalRequest> mRequest;
UniquePtr<SerializedStackHolder> mOriginStack;
public:
@ -362,14 +362,14 @@ class MainThreadFetchRunnable : public Runnable {
const ClientInfo& aClientInfo,
const Maybe<ServiceWorkerDescriptor>& aController,
nsICSPEventListener* aCSPEventListener,
InternalRequest* aRequest,
SafeRefPtr<InternalRequest> aRequest,
UniquePtr<SerializedStackHolder>&& aOriginStack)
: Runnable("dom::MainThreadFetchRunnable"),
mResolver(aResolver),
mClientInfo(aClientInfo),
mController(aController),
mCSPEventListener(aCSPEventListener),
mRequest(aRequest),
mRequest(std::move(aRequest)),
mOriginStack(std::move(aOriginStack)) {
MOZ_ASSERT(mResolver);
}
@ -396,7 +396,7 @@ class MainThreadFetchRunnable : public Runnable {
MOZ_ASSERT(loadGroup);
// We don't track if a worker is spawned from a tracking script for now,
// so pass false as the last argument to FetchDriver().
fetch = new FetchDriver(mRequest, principal, loadGroup,
fetch = new FetchDriver(mRequest.clonePtr(), principal, loadGroup,
workerPrivate->MainThreadEventTarget(),
workerPrivate->CookieJarSettings(),
workerPrivate->GetPerformanceStorage(), false);
@ -455,7 +455,7 @@ already_AddRefed<Promise> FetchRequest(nsIGlobalObject* aGlobal,
return nullptr;
}
RefPtr<InternalRequest> r = request->GetInternalRequest();
SafeRefPtr<InternalRequest> r = request->GetInternalRequest();
RefPtr<AbortSignalImpl> signalImpl = request->GetSignalImpl();
if (signalImpl && signalImpl->Aborted()) {
@ -508,10 +508,11 @@ already_AddRefed<Promise> FetchRequest(nsIGlobalObject* aGlobal,
RefPtr<MainThreadFetchResolver> resolver = new MainThreadFetchResolver(
p, observer, signalImpl, request->MozErrors());
RefPtr<FetchDriver> fetch = new FetchDriver(
r, principal, loadGroup, aGlobal->EventTargetFor(TaskCategory::Other),
cookieJarSettings, nullptr, // PerformanceStorage
isTrackingFetch);
RefPtr<FetchDriver> fetch =
new FetchDriver(std::move(r), principal, loadGroup,
aGlobal->EventTargetFor(TaskCategory::Other),
cookieJarSettings, nullptr, // PerformanceStorage
isTrackingFetch);
fetch->SetDocument(doc);
resolver->SetLoadGroup(loadGroup);
aRv = fetch->Fetch(signalImpl, resolver);
@ -547,7 +548,7 @@ already_AddRefed<Promise> FetchRequest(nsIGlobalObject* aGlobal,
RefPtr<MainThreadFetchRunnable> run = new MainThreadFetchRunnable(
resolver, clientInfo.ref(), worker->GlobalScope()->GetController(),
worker->CSPEventListener(), r, std::move(stack));
worker->CSPEventListener(), std::move(r), std::move(stack));
worker->DispatchToMainThread(run.forget());
}

View File

@ -74,13 +74,10 @@ void GetBlobURISpecFromChannel(nsIRequest* aRequest, nsCString& aBlobURISpec) {
uri->GetSpec(aBlobURISpec);
}
bool ShouldCheckSRI(const InternalRequest* const aRequest,
const InternalResponse* const aResponse) {
MOZ_DIAGNOSTIC_ASSERT(aRequest);
MOZ_DIAGNOSTIC_ASSERT(aResponse);
return !aRequest->GetIntegrity().IsEmpty() &&
aResponse->Type() != ResponseType::Error;
bool ShouldCheckSRI(const InternalRequest& aRequest,
const InternalResponse& aResponse) {
return !aRequest.GetIntegrity().IsEmpty() &&
aResponse.Type() != ResponseType::Error;
}
} // anonymous namespace
@ -323,15 +320,15 @@ AlternativeDataStreamListener::CheckListenerChain() { return NS_OK; }
NS_IMPL_ISUPPORTS(FetchDriver, nsIStreamListener, nsIChannelEventSink,
nsIInterfaceRequestor, nsIThreadRetargetableStreamListener)
FetchDriver::FetchDriver(InternalRequest* aRequest, nsIPrincipal* aPrincipal,
nsILoadGroup* aLoadGroup,
FetchDriver::FetchDriver(SafeRefPtr<InternalRequest> aRequest,
nsIPrincipal* aPrincipal, nsILoadGroup* aLoadGroup,
nsIEventTarget* aMainThreadEventTarget,
nsICookieJarSettings* aCookieJarSettings,
PerformanceStorage* aPerformanceStorage,
bool aIsTrackingFetch)
: mPrincipal(aPrincipal),
mLoadGroup(aLoadGroup),
mRequest(aRequest),
mRequest(std::move(aRequest)),
mMainThreadEventTarget(aMainThreadEventTarget),
mCookieJarSettings(aCookieJarSettings),
mPerformanceStorage(aPerformanceStorage),
@ -346,7 +343,7 @@ FetchDriver::FetchDriver(InternalRequest* aRequest, nsIPrincipal* aPrincipal,
{
AssertIsOnMainThread();
MOZ_ASSERT(aRequest);
MOZ_ASSERT(mRequest);
MOZ_ASSERT(aPrincipal);
MOZ_ASSERT(aMainThreadEventTarget);
}
@ -592,7 +589,7 @@ nsresult FetchDriver::HttpFetch(
}
rv = FetchUtil::SetRequestReferrer(mPrincipal, mDocument, httpChan,
mRequest);
*mRequest);
NS_ENSURE_SUCCESS(rv, rv);
// Bug 1120722 - Authorization will be handled later.
@ -759,7 +756,7 @@ already_AddRefed<InternalResponse> FetchDriver::BeginAndGetFilteredResponse(
MOZ_ASSERT(filteredResponse);
MOZ_ASSERT(mObserver);
if (!ShouldCheckSRI(mRequest, filteredResponse)) {
if (!ShouldCheckSRI(*mRequest, *filteredResponse)) {
mObserver->OnResponseAvailable(filteredResponse);
#ifdef DEBUG
mResponseAvailableCalled = true;
@ -1044,7 +1041,7 @@ FetchDriver::OnStartRequest(nsIRequest* aRequest) {
}
// From "Main Fetch" step 19: SRI-part1.
if (ShouldCheckSRI(mRequest, mResponse) && mSRIMetadata.IsEmpty()) {
if (ShouldCheckSRI(*mRequest, *mResponse) && mSRIMetadata.IsEmpty()) {
nsIConsoleReportCollector* reporter = nullptr;
if (mObserver) {
reporter = mObserver->GetReporter();
@ -1174,7 +1171,7 @@ FetchDriver::OnDataAvailable(nsIRequest* aRequest, nsIInputStream* aInputStream,
// Note: Avoid checking the hidden opaque body.
nsresult rv;
if (mResponse->Type() != ResponseType::Opaque &&
ShouldCheckSRI(mRequest, mResponse)) {
ShouldCheckSRI(*mRequest, *mResponse)) {
MOZ_ASSERT(mSRIDataVerifier);
SRIVerifierAndOutputHolder holder(mSRIDataVerifier.get(),
@ -1230,7 +1227,7 @@ FetchDriver::OnStopRequest(nsIRequest* aRequest, nsresult aStatusCode) {
MOZ_ASSERT(!mResponse->IsError());
// From "Main Fetch" step 19: SRI-part3.
if (ShouldCheckSRI(mRequest, mResponse)) {
if (ShouldCheckSRI(*mRequest, *mResponse)) {
MOZ_ASSERT(mSRIDataVerifier);
nsCOMPtr<nsIChannel> channel = do_QueryInterface(aRequest);
@ -1287,7 +1284,7 @@ void FetchDriver::FinishOnStopRequest(
if (mObserver) {
// From "Main Fetch" step 19.1, 19.2: Process response.
if (ShouldCheckSRI(mRequest, mResponse)) {
if (ShouldCheckSRI(*mRequest, *mResponse)) {
MOZ_ASSERT(mResponse);
mObserver->OnResponseAvailable(mResponse);
#ifdef DEBUG

View File

@ -13,6 +13,7 @@
#include "nsIThreadRetargetableStreamListener.h"
#include "mozilla/ConsoleReportCollector.h"
#include "mozilla/dom/AbortSignal.h"
#include "mozilla/dom/SafeRefPtr.h"
#include "mozilla/dom/SerializedStackHolder.h"
#include "mozilla/dom/SRIMetadata.h"
#include "mozilla/RefPtr.h"
@ -100,7 +101,7 @@ class FetchDriver final : public nsIStreamListener,
NS_DECL_NSIINTERFACEREQUESTOR
NS_DECL_NSITHREADRETARGETABLESTREAMLISTENER
FetchDriver(InternalRequest* aRequest, nsIPrincipal* aPrincipal,
FetchDriver(SafeRefPtr<InternalRequest> aRequest, nsIPrincipal* aPrincipal,
nsILoadGroup* aLoadGroup, nsIEventTarget* aMainThreadEventTarget,
nsICookieJarSettings* aCookieJarSettings,
PerformanceStorage* aPerformanceStorage, bool aIsTrackingFetch);
@ -130,7 +131,7 @@ class FetchDriver final : public nsIStreamListener,
private:
nsCOMPtr<nsIPrincipal> mPrincipal;
nsCOMPtr<nsILoadGroup> mLoadGroup;
RefPtr<InternalRequest> mRequest;
SafeRefPtr<InternalRequest> mRequest;
RefPtr<InternalResponse> mResponse;
nsCOMPtr<nsIOutputStream> mPipeOutputStream;
RefPtr<FetchDriverObserver> mObserver;

View File

@ -111,14 +111,14 @@ bool FetchUtil::ExtractHeader(nsACString::const_iterator& aStart,
// static
nsresult FetchUtil::SetRequestReferrer(nsIPrincipal* aPrincipal, Document* aDoc,
nsIHttpChannel* aChannel,
InternalRequest* aRequest) {
InternalRequest& aRequest) {
MOZ_ASSERT(NS_IsMainThread());
nsresult rv = NS_OK;
nsAutoString referrer;
aRequest->GetReferrer(referrer);
aRequest.GetReferrer(referrer);
ReferrerPolicy policy = aRequest->ReferrerPolicy_();
ReferrerPolicy policy = aRequest.ReferrerPolicy_();
nsCOMPtr<nsIReferrerInfo> referrerInfo;
if (referrer.IsEmpty()) {
// This is the case requests referrer is "no-referrer"
@ -150,7 +150,7 @@ nsresult FetchUtil::SetRequestReferrer(nsIPrincipal* aPrincipal, Document* aDoc,
// Step 8 https://fetch.spec.whatwg.org/#main-fetch
// If requests referrer is not "no-referrer", set requests referrer to
// the result of invoking determine requests referrer.
aRequest->SetReferrer(computedReferrerSpec);
aRequest.SetReferrer(computedReferrerSpec);
return NS_OK;
}

View File

@ -51,7 +51,7 @@ class FetchUtil final {
static nsresult SetRequestReferrer(nsIPrincipal* aPrincipal, Document* aDoc,
nsIHttpChannel* aChannel,
InternalRequest* aRequest);
InternalRequest& aRequest);
/**
* Check that the given object is a Response and, if so, stream to the given

View File

@ -22,13 +22,13 @@
namespace mozilla {
namespace dom {
// The global is used to extract the principal.
already_AddRefed<InternalRequest> InternalRequest::GetRequestConstructorCopy(
SafeRefPtr<InternalRequest> InternalRequest::GetRequestConstructorCopy(
nsIGlobalObject* aGlobal, ErrorResult& aRv) const {
MOZ_RELEASE_ASSERT(!mURLList.IsEmpty(),
"Internal Request's urlList should not be empty when "
"copied from constructor.");
RefPtr<InternalRequest> copy =
new InternalRequest(mURLList.LastElement(), mFragment);
auto copy =
MakeSafeRefPtr<InternalRequest>(mURLList.LastElement(), mFragment);
copy->SetMethod(mMethod);
copy->mHeaders = new InternalHeaders(*mHeaders);
copy->SetUnsafeRequest();
@ -53,14 +53,14 @@ already_AddRefed<InternalRequest> InternalRequest::GetRequestConstructorCopy(
copy->mContentPolicyTypeOverridden = mContentPolicyTypeOverridden;
copy->mPreferredAlternativeDataType = mPreferredAlternativeDataType;
return copy.forget();
return copy;
}
already_AddRefed<InternalRequest> InternalRequest::Clone() {
RefPtr<InternalRequest> clone = new InternalRequest(*this);
SafeRefPtr<InternalRequest> InternalRequest::Clone() {
auto clone = MakeSafeRefPtr<InternalRequest>(*this, ConstructorGuard{});
if (!mBodyStream) {
return clone.forget();
return clone;
}
nsCOMPtr<nsIInputStream> clonedBody;
@ -76,7 +76,7 @@ already_AddRefed<InternalRequest> InternalRequest::Clone() {
if (replacementBody) {
mBodyStream.swap(replacementBody);
}
return clone.forget();
return clone;
}
InternalRequest::InternalRequest(const nsACString& aURL,
const nsACString& aFragment)
@ -116,7 +116,8 @@ InternalRequest::InternalRequest(
MOZ_ASSERT(!aURL.IsEmpty());
AddURL(aURL, aFragment);
}
InternalRequest::InternalRequest(const InternalRequest& aOther)
InternalRequest::InternalRequest(const InternalRequest& aOther,
ConstructorGuard)
: mMethod(aOther.mMethod),
mURLList(aOther.mURLList.Clone()),
mHeaders(new InternalHeaders(*aOther.mHeaders)),

View File

@ -10,6 +10,7 @@
#include "mozilla/dom/HeadersBinding.h"
#include "mozilla/dom/InternalHeaders.h"
#include "mozilla/dom/RequestBinding.h"
#include "mozilla/dom/SafeRefPtr.h"
#include "mozilla/LoadTainting.h"
#include "mozilla/UniquePtr.h"
@ -72,11 +73,11 @@ class IPCInternalRequest;
class Request;
#define kFETCH_CLIENT_REFERRER_STR "about:client"
class InternalRequest final {
class InternalRequest final : public AtomicSafeRefCounted<InternalRequest> {
friend class Request;
public:
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(InternalRequest)
MOZ_DECLARE_REFCOUNTED_TYPENAME(InternalRequest)
InternalRequest(const nsACString& aURL, const nsACString& aFragment);
InternalRequest(const nsACString& aURL, const nsACString& aFragment,
const nsACString& aMethod,
@ -94,7 +95,7 @@ class InternalRequest final {
void ToIPC(IPCInternalRequest* aIPCRequest, M* aManager,
UniquePtr<mozilla::ipc::AutoIPCStream>& aAutoStream);
already_AddRefed<InternalRequest> Clone();
SafeRefPtr<InternalRequest> Clone();
void GetMethod(nsCString& aMethod) const { aMethod.Assign(mMethod); }
@ -264,7 +265,7 @@ class InternalRequest final {
void SetUnsafeRequest() { mUnsafeRequest = true; }
InternalHeaders* Headers() { return mHeaders; }
InternalHeaders* Headers() const { return mHeaders; }
void SetHeaders(InternalHeaders* aHeaders) {
MOZ_ASSERT(aHeaders);
@ -280,7 +281,7 @@ class InternalRequest final {
// Will return the original stream!
// Use a tee or copy if you don't want to erase the original.
void GetBody(nsIInputStream** aStream, int64_t* aBodyLength = nullptr) {
void GetBody(nsIInputStream** aStream, int64_t* aBodyLength = nullptr) const {
nsCOMPtr<nsIInputStream> s = mBodyStream;
s.forget(aStream);
@ -300,7 +301,7 @@ class InternalRequest final {
const nsAString& BodyLocalPath() const { return mBodyLocalPath; }
// The global is used as the client for the new object.
already_AddRefed<InternalRequest> GetRequestConstructorCopy(
SafeRefPtr<InternalRequest> GetRequestConstructorCopy(
nsIGlobalObject* aGlobal, ErrorResult& aRv) const;
bool IsNavigationRequest() const;
@ -335,12 +336,18 @@ class InternalRequest final {
mPreferredAlternativeDataType = aDataType;
}
private:
// Does not copy mBodyStream. Use fallible Clone() for complete copy.
explicit InternalRequest(const InternalRequest& aOther);
~InternalRequest();
InternalRequest(const InternalRequest& aOther) = delete;
private:
struct ConstructorGuard {};
public:
// Does not copy mBodyStream. Use fallible Clone() for complete copy.
InternalRequest(const InternalRequest& aOther, ConstructorGuard);
private:
// Map the content policy type to the associated fetch destination, as defined
// by the spec at https://fetch.spec.whatwg.org/#concept-request-destination.
// Note that while the HTML spec for the "Link" element and its "as" attribute

View File

@ -52,12 +52,12 @@ NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(Request)
NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
NS_INTERFACE_MAP_END_INHERITING(FetchBody<Request>)
Request::Request(nsIGlobalObject* aOwner, InternalRequest* aRequest,
Request::Request(nsIGlobalObject* aOwner, SafeRefPtr<InternalRequest> aRequest,
AbortSignal* aSignal)
: FetchBody<Request>(aOwner), mRequest(aRequest) {
MOZ_ASSERT(aRequest->Headers()->Guard() == HeadersGuardEnum::Immutable ||
aRequest->Headers()->Guard() == HeadersGuardEnum::Request ||
aRequest->Headers()->Guard() == HeadersGuardEnum::Request_no_cors);
: FetchBody<Request>(aOwner), mRequest(std::move(aRequest)) {
MOZ_ASSERT(mRequest->Headers()->Guard() == HeadersGuardEnum::Immutable ||
mRequest->Headers()->Guard() == HeadersGuardEnum::Request ||
mRequest->Headers()->Guard() == HeadersGuardEnum::Request_no_cors);
SetMimeType();
if (aSignal) {
@ -72,9 +72,8 @@ Request::Request(nsIGlobalObject* aOwner, InternalRequest* aRequest,
Request::~Request() = default;
already_AddRefed<InternalRequest> Request::GetInternalRequest() {
RefPtr<InternalRequest> r = mRequest;
return r.forget();
SafeRefPtr<InternalRequest> Request::GetInternalRequest() {
return mRequest.clonePtr();
}
namespace {
@ -276,7 +275,7 @@ already_AddRefed<Request> Request::Constructor(nsIGlobalObject* aGlobal,
const RequestInit& aInit,
ErrorResult& aRv) {
bool hasCopiedBody = false;
RefPtr<InternalRequest> request;
SafeRefPtr<InternalRequest> request;
RefPtr<AbortSignal> signal;
@ -322,7 +321,8 @@ already_AddRefed<Request> Request::Constructor(nsIGlobalObject* aGlobal,
if (aRv.Failed()) {
return nullptr;
}
request = new InternalRequest(NS_ConvertUTF16toUTF8(requestURL), fragment);
request = MakeSafeRefPtr<InternalRequest>(NS_ConvertUTF16toUTF8(requestURL),
fragment);
}
request = request->GetRequestConstructorCopy(aGlobal, aRv);
if (NS_WARN_IF(aRv.Failed())) {
@ -593,7 +593,7 @@ already_AddRefed<Request> Request::Constructor(nsIGlobalObject* aGlobal,
}
}
RefPtr<Request> domRequest = new Request(aGlobal, request, signal);
RefPtr<Request> domRequest = new Request(aGlobal, std::move(request), signal);
domRequest->SetMimeType();
if (aInput.IsRequest()) {
@ -621,13 +621,14 @@ already_AddRefed<Request> Request::Clone(ErrorResult& aRv) {
return nullptr;
}
RefPtr<InternalRequest> ir = mRequest->Clone();
SafeRefPtr<InternalRequest> ir = mRequest->Clone();
if (!ir) {
aRv.Throw(NS_ERROR_FAILURE);
return nullptr;
}
RefPtr<Request> request = new Request(mOwner, ir, GetOrCreateSignal());
RefPtr<Request> request =
new Request(mOwner, std::move(ir), GetOrCreateSignal());
return request.forget();
}

View File

@ -15,6 +15,7 @@
// Required here due to certain WebIDL enums/classes being declared in both
// files.
#include "mozilla/dom/RequestBinding.h"
#include "mozilla/dom/SafeRefPtr.h"
namespace mozilla {
namespace dom {
@ -29,7 +30,7 @@ class Request final : public FetchBody<Request>, public nsWrapperCache {
FetchBody<Request>)
public:
Request(nsIGlobalObject* aOwner, InternalRequest* aRequest,
Request(nsIGlobalObject* aOwner, SafeRefPtr<InternalRequest> aRequest,
AbortSignal* aSignal);
JSObject* WrapObject(JSContext* aCx,
@ -114,7 +115,7 @@ class Request final : public FetchBody<Request>, public nsWrapperCache {
already_AddRefed<Request> Clone(ErrorResult& aRv);
already_AddRefed<InternalRequest> GetInternalRequest();
SafeRefPtr<InternalRequest> GetInternalRequest();
const UniquePtr<mozilla::ipc::PrincipalInfo>& GetPrincipalInfo() const {
return mRequest->GetPrincipalInfo();
@ -128,7 +129,7 @@ class Request final : public FetchBody<Request>, public nsWrapperCache {
private:
~Request();
RefPtr<InternalRequest> mRequest;
SafeRefPtr<InternalRequest> mRequest;
// Lazily created.
RefPtr<Headers> mHeaders;

View File

@ -204,8 +204,7 @@ void SendReports(nsTArray<ReportDeliver::ReportData>& aReports,
return;
}
RefPtr<InternalRequest> internalRequest =
new InternalRequest(uriSpec, uriFragment);
auto internalRequest = MakeSafeRefPtr<InternalRequest>(uriSpec, uriFragment);
internalRequest->SetMethod(NS_LITERAL_CSTRING("POST"));
internalRequest->SetBody(streamBody, body.Length());
@ -215,7 +214,8 @@ void SendReports(nsTArray<ReportDeliver::ReportData>& aReports,
internalRequest->SetMode(RequestMode::Cors);
internalRequest->SetCredentialsMode(RequestCredentials::Include);
RefPtr<Request> request = new Request(globalObject, internalRequest, nullptr);
RefPtr<Request> request =
new Request(globalObject, std::move(internalRequest), nullptr);
RequestOrUSVString fetchInput;
fetchInput.SetAsRequest() = request;

View File

@ -321,7 +321,7 @@ nsresult GetIPCInternalRequest(nsIInterceptedChannel* aChannel,
NS_ENSURE_SUCCESS(rv, rv);
}
RefPtr<InternalRequest> internalRequest = new InternalRequest(
auto internalRequest = MakeSafeRefPtr<InternalRequest>(
spec, fragment, method, internalHeaders.forget(), cacheMode, requestMode,
requestRedirect, requestCredentials, referrer, referrerPolicy,
contentPolicyType, integrity);

View File

@ -57,7 +57,7 @@ void FetchEventOpProxyChild::Initialize(
MOZ_ASSERT(RemoteWorkerService::Thread()->IsOnCurrentThread());
MOZ_ASSERT(!mOp);
mInternalRequest = new InternalRequest(aArgs.internalRequest());
mInternalRequest = MakeSafeRefPtr<InternalRequest>(aArgs.internalRequest());
RemoteWorkerChild* manager = static_cast<RemoteWorkerChild*>(Manager());
MOZ_ASSERT(manager);
@ -135,11 +135,11 @@ void FetchEventOpProxyChild::Initialize(
manager->MaybeStartOp(std::move(op));
}
RefPtr<InternalRequest> FetchEventOpProxyChild::ExtractInternalRequest() {
SafeRefPtr<InternalRequest> FetchEventOpProxyChild::ExtractInternalRequest() {
MOZ_ASSERT(IsCurrentThreadRunningWorker());
MOZ_ASSERT(mInternalRequest);
return RefPtr<InternalRequest>(std::move(mInternalRequest));
return std::move(mInternalRequest);
}
void FetchEventOpProxyChild::ActorDestroy(ActorDestroyReason) {

View File

@ -32,7 +32,7 @@ class FetchEventOpProxyChild final : public PFetchEventOpProxyChild {
void Initialize(const ServiceWorkerFetchEventOpArgs& aArgs);
// Must only be called once and on a worker thread.
RefPtr<InternalRequest> ExtractInternalRequest();
SafeRefPtr<InternalRequest> ExtractInternalRequest();
private:
~FetchEventOpProxyChild() = default;
@ -45,7 +45,7 @@ class FetchEventOpProxyChild final : public PFetchEventOpProxyChild {
RefPtr<FetchEventOp> mOp;
// Initialized on RemoteWorkerService::Thread, read on a worker thread.
RefPtr<InternalRequest> mInternalRequest;
SafeRefPtr<InternalRequest> mInternalRequest;
};
} // namespace dom

View File

@ -788,7 +788,7 @@ void FetchEvent::RespondWith(JSContext* aCx, Promise& aArg, ErrorResult& aRv) {
uint32_t column = 0;
nsJSUtils::GetCallingLocation(aCx, spec, &line, &column);
RefPtr<InternalRequest> ir = mRequest->GetInternalRequest();
SafeRefPtr<InternalRequest> ir = mRequest->GetInternalRequest();
nsAutoCString requestURL;
ir->GetURL(requestURL);
@ -838,7 +838,7 @@ void FetchEvent::PreventDefault(JSContext* aCx, CallerType aCallerType) {
void FetchEvent::ReportCanceled() {
MOZ_ASSERT(!mPreventDefaultScriptSpec.IsEmpty());
RefPtr<InternalRequest> ir = mRequest->GetInternalRequest();
SafeRefPtr<InternalRequest> ir = mRequest->GetInternalRequest();
nsAutoCString url;
ir->GetURL(url);

View File

@ -1503,7 +1503,8 @@ nsresult FetchEventOp::DispatchFetchEvent(JSContext* aCx,
* correct thread before creating this op, so we can take its saved
* InternalRequest.
*/
RefPtr<InternalRequest> internalRequest = mActor->ExtractInternalRequest();
SafeRefPtr<InternalRequest> internalRequest =
mActor->ExtractInternalRequest();
/**
* Step 2: get the worker's global object
@ -1521,7 +1522,7 @@ nsresult FetchEventOp::DispatchFetchEvent(JSContext* aCx,
* which should be aborted if the loading is aborted. See but 1394102.
*/
RefPtr<Request> request =
new Request(globalObjectAsSupports, internalRequest, nullptr);
new Request(globalObjectAsSupports, internalRequest.clonePtr(), nullptr);
MOZ_ASSERT_IF(internalRequest->IsNavigationRequest(),
request->Redirect() == RequestRedirect::Manual);

View File

@ -1422,7 +1422,7 @@ class FetchEventRunnable : public ExtendableFunctionalEventWorkerRunnable,
result.SuppressException();
return false;
}
RefPtr<InternalRequest> internalReq = new InternalRequest(
auto internalReq = MakeSafeRefPtr<InternalRequest>(
mSpec, mFragment, mMethod, internalHeaders.forget(), mCacheMode,
mRequestMode, mRequestRedirect, mRequestCredentials, mReferrer,
mReferrerPolicy, mContentPolicyType, mIntegrity);
@ -1449,7 +1449,8 @@ class FetchEventRunnable : public ExtendableFunctionalEventWorkerRunnable,
// TODO This request object should be created with a AbortSignal object
// which should be aborted if the loading is aborted. See bug 1394102.
RefPtr<Request> request = new Request(global, internalReq, nullptr);
RefPtr<Request> request =
new Request(global, internalReq.clonePtr(), nullptr);
MOZ_ASSERT_IF(internalReq->IsNavigationRequest(),
request->Redirect() == RequestRedirect::Manual);