Issue #2736 - Part 14: Make CSP-enabled available to workers.

This commit is contained in:
Moonchild 2025-05-13 16:35:35 +02:00 • committed by roytam1
commit 53a6f6349d
5 changed files with 79 additions and 39 deletions

View file

@ -8980,6 +8980,25 @@ nsContentUtils::StreamsEnabled(JSContext* aCx, JSObject* aObj)
return workerPrivate->StreamsEnabled(); return workerPrivate->StreamsEnabled();
} }
// static
bool
nsContentUtils::CSPEnabled(JSContext* aCx, JSObject* aObj)
{
if (NS_IsMainThread()) {
return Preferences::GetBool("security.csp.enabled", true);
}
using namespace workers;
// Otherwise, check the pref via the WorkerPrivate
WorkerPrivate* workerPrivate = GetWorkerPrivateFromContext(aCx);
if (!workerPrivate) {
return false;
}
return workerPrivate->CSPEnabled();
}
// static // static
bool bool
nsContentUtils::IsNonSubresourceRequest(nsIChannel* aChannel) nsContentUtils::IsNonSubresourceRequest(nsIChannel* aChannel)

View file

@ -2798,6 +2798,8 @@ public:
static bool PushEnabled(JSContext* aCx, JSObject* aObj); static bool PushEnabled(JSContext* aCx, JSObject* aObj);
static bool CSPEnabled(JSContext* aCx, JSObject* aObj);
static bool StreamsEnabled(JSContext* aCx, JSObject* aObj); static bool StreamsEnabled(JSContext* aCx, JSObject* aObj);
static bool IsNonSubresourceRequest(nsIChannel* aChannel); static bool IsNonSubresourceRequest(nsIChannel* aChannel);

View file

@ -578,7 +578,7 @@ ContentSecurityPolicyAllows(JSContext* aCx, JS::HandleValue aValue)
WorkerPrivate* worker = GetWorkerPrivateFromContext(aCx); WorkerPrivate* worker = GetWorkerPrivateFromContext(aCx);
worker->AssertIsOnWorkerThread(); worker->AssertIsOnWorkerThread();
if (worker->GetReportCSPViolations()) { if (worker->CSPEnabled() && worker->GetReportCSPViolations()) {
JS::Rooted<JSString*> jsString(aCx, JS::ToString(aCx, aValue)); JS::Rooted<JSString*> jsString(aCx, JS::ToString(aCx, aValue));
if (NS_WARN_IF(!jsString)) { if (NS_WARN_IF(!jsString)) {
JS_ClearPendingException(aCx); JS_ClearPendingException(aCx);
@ -2715,6 +2715,7 @@ LogViolationDetailsRunnable::MainThreadRun()
{ {
AssertIsOnMainThread(); AssertIsOnMainThread();
if (mWorkerPrivate->CSPEnabled()) {
nsIContentSecurityPolicy* csp = mWorkerPrivate->GetCSP(); nsIContentSecurityPolicy* csp = mWorkerPrivate->GetCSP();
if (csp) { if (csp) {
if (mWorkerPrivate->GetReportCSPViolations()) { if (mWorkerPrivate->GetReportCSPViolations()) {
@ -2723,6 +2724,7 @@ LogViolationDetailsRunnable::MainThreadRun()
EmptyString(), EmptyString()); EmptyString(), EmptyString());
} }
} }
}
return true; return true;
} }

View file

@ -1102,6 +1102,7 @@ private:
return NS_ERROR_NOT_AVAILABLE; return NS_ERROR_NOT_AVAILABLE;
} }
if (mWorkerPrivate->CSPEnabled()) {
httpChannel->GetResponseHeader( httpChannel->GetResponseHeader(
NS_LITERAL_CSTRING("content-security-policy"), NS_LITERAL_CSTRING("content-security-policy"),
tCspHeaderValue); tCspHeaderValue);
@ -1114,6 +1115,7 @@ private:
NS_LITERAL_CSTRING("referrer-policy"), NS_LITERAL_CSTRING("referrer-policy"),
tRPHeaderCValue); tRPHeaderCValue);
} }
}
// May be null. // May be null.
nsIDocument* parentDoc = mWorkerPrivate->GetDocument(); nsIDocument* parentDoc = mWorkerPrivate->GetDocument();
@ -1164,6 +1166,7 @@ private:
// by using the SRICheck module // by using the SRICheck module
MOZ_LOG(SRILogHelper::GetSriLog(), mozilla::LogLevel::Debug, MOZ_LOG(SRILogHelper::GetSriLog(), mozilla::LogLevel::Debug,
("Scriptloader::Load, SRI required but not supported in workers")); ("Scriptloader::Load, SRI required but not supported in workers"));
if (mWorkerPrivate->CSPEnabled()) {
nsCOMPtr<nsIContentSecurityPolicy> wcsp; nsCOMPtr<nsIContentSecurityPolicy> wcsp;
chanLoadInfo->LoadingPrincipal()->GetCsp(getter_AddRefs(wcsp)); chanLoadInfo->LoadingPrincipal()->GetCsp(getter_AddRefs(wcsp));
MOZ_ASSERT(wcsp, "We should have a CSP for the worker here"); MOZ_ASSERT(wcsp, "We should have a CSP for the worker here");
@ -1172,6 +1175,7 @@ private:
nsIContentSecurityPolicy::VIOLATION_TYPE_REQUIRE_SRI_FOR_SCRIPT, nsIContentSecurityPolicy::VIOLATION_TYPE_REQUIRE_SRI_FOR_SCRIPT,
aLoadInfo.mURL, EmptyString(), 0, 0, EmptyString(), EmptyString()); aLoadInfo.mURL, EmptyString(), 0, 0, EmptyString(), EmptyString());
} }
}
return NS_ERROR_SRI_CORRUPT; return NS_ERROR_SRI_CORRUPT;
} }
@ -1242,7 +1246,9 @@ private:
// We did inherit CSP in bug 1223647. If we do not already have a CSP, we // We did inherit CSP in bug 1223647. If we do not already have a CSP, we
// should get it from the HTTP headers on the worker script. // should get it from the HTTP headers on the worker script.
if (!mWorkerPrivate->GetCSP() && CSPService::sCSPEnabled) { if (mWorkerPrivate->CSPEnabled() &&
!mWorkerPrivate->GetCSP() &&
CSPService::sCSPEnabled) {
rv = mWorkerPrivate->SetCSPFromHeaderValues(tCspHeaderValue, rv = mWorkerPrivate->SetCSPFromHeaderValues(tCspHeaderValue,
tCspROHeaderValue); tCspROHeaderValue);
NS_ENSURE_SUCCESS(rv, rv); NS_ENSURE_SUCCESS(rv, rv);
@ -1320,9 +1326,11 @@ private:
MOZ_ALWAYS_SUCCEEDS(responsePrincipal->Equals(principal, &equal)); MOZ_ALWAYS_SUCCEEDS(responsePrincipal->Equals(principal, &equal));
MOZ_DIAGNOSTIC_ASSERT(equal); MOZ_DIAGNOSTIC_ASSERT(equal);
if (mWorkerPrivate->CSPEnabled()) {
nsCOMPtr<nsIContentSecurityPolicy> csp; nsCOMPtr<nsIContentSecurityPolicy> csp;
MOZ_ALWAYS_SUCCEEDS(responsePrincipal->GetCsp(getter_AddRefs(csp))); MOZ_ALWAYS_SUCCEEDS(responsePrincipal->GetCsp(getter_AddRefs(csp)));
MOZ_DIAGNOSTIC_ASSERT(!csp); MOZ_DIAGNOSTIC_ASSERT(!csp);
}
#endif #endif
mWorkerPrivate->InitChannelInfo(aChannelInfo); mWorkerPrivate->InitChannelInfo(aChannelInfo);
@ -1335,10 +1343,12 @@ private:
rv = mWorkerPrivate->SetPrincipalOnMainThread(responsePrincipal, loadGroup); rv = mWorkerPrivate->SetPrincipalOnMainThread(responsePrincipal, loadGroup);
MOZ_DIAGNOSTIC_ASSERT(NS_SUCCEEDED(rv)); MOZ_DIAGNOSTIC_ASSERT(NS_SUCCEEDED(rv));
if (mWorkerPrivate->CSPEnabled()) {
rv = mWorkerPrivate->SetCSPFromHeaderValues(aCSPHeaderValue, rv = mWorkerPrivate->SetCSPFromHeaderValues(aCSPHeaderValue,
aCSPReportOnlyHeaderValue); aCSPReportOnlyHeaderValue);
MOZ_DIAGNOSTIC_ASSERT(NS_SUCCEEDED(rv)); MOZ_DIAGNOSTIC_ASSERT(NS_SUCCEEDED(rv));
} }
}
if (NS_SUCCEEDED(rv)) { if (NS_SUCCEEDED(rv)) {
DataReceived(); DataReceived();
@ -1357,9 +1367,13 @@ private:
// XHR Params Allowed // XHR Params Allowed
mWorkerPrivate->SetXHRParamsAllowed(parent->XHRParamsAllowed()); mWorkerPrivate->SetXHRParamsAllowed(parent->XHRParamsAllowed());
if (mWorkerPrivate->CSPEnabled()) {
// Set Eval and ContentSecurityPolicy // Set Eval and ContentSecurityPolicy
mWorkerPrivate->SetCSP(parent->GetCSP()); mWorkerPrivate->SetCSP(parent->GetCSP());
mWorkerPrivate->SetEvalAllowed(parent->IsEvalAllowed()); mWorkerPrivate->SetEvalAllowed(parent->IsEvalAllowed());
} else {
mWorkerPrivate->SetEvalAllowed(true);
}
} }
} }
} }
@ -1754,10 +1768,12 @@ CacheScriptLoader::ResolvedCallback(JSContext* aCx,
InternalHeaders* headers = response->GetInternalHeaders(); InternalHeaders* headers = response->GetInternalHeaders();
IgnoredErrorResult ignored; IgnoredErrorResult ignored;
if (nsContentUtils::CSPEnabled(aCx, obj)) {
headers->Get(NS_LITERAL_CSTRING("content-security-policy"), headers->Get(NS_LITERAL_CSTRING("content-security-policy"),
mCSPHeaderValue, ignored); mCSPHeaderValue, ignored);
headers->Get(NS_LITERAL_CSTRING("content-security-policy-report-only"), headers->Get(NS_LITERAL_CSTRING("content-security-policy-report-only"),
mCSPReportOnlyHeaderValue, ignored); mCSPReportOnlyHeaderValue, ignored);
}
nsCOMPtr<nsIInputStream> inputStream; nsCOMPtr<nsIInputStream> inputStream;
response->GetBody(getter_AddRefs(inputStream)); response->GetBody(getter_AddRefs(inputStream));

View file

@ -40,6 +40,7 @@ WORKER_SIMPLE_PREF("gfx.offscreencanvas.enabled", OffscreenCanvasEnabled, OFFSCR
WORKER_SIMPLE_PREF("dom.webkitBlink.dirPicker.enabled", WebkitBlinkDirectoryPickerEnabled, DOM_WEBKITBLINK_DIRPICKER_WEBKITBLINK) WORKER_SIMPLE_PREF("dom.webkitBlink.dirPicker.enabled", WebkitBlinkDirectoryPickerEnabled, DOM_WEBKITBLINK_DIRPICKER_WEBKITBLINK)
WORKER_SIMPLE_PREF("dom.abortController.enabled", AbortControllerEnabled, ABORTCONTROLLER_ENABLED) WORKER_SIMPLE_PREF("dom.abortController.enabled", AbortControllerEnabled, ABORTCONTROLLER_ENABLED)
WORKER_SIMPLE_PREF("dom.fetchObserver.enabled", FetchObserverEnabled, FETCHOBSERVER_ENABLED) WORKER_SIMPLE_PREF("dom.fetchObserver.enabled", FetchObserverEnabled, FETCHOBSERVER_ENABLED)
WORKER_SIMPLE_PREF("security.csp.enable", CSPEnabled, CSP_ENABLED)
WORKER_PREF("dom.workers.latestJSVersion", JSVersionChanged) WORKER_PREF("dom.workers.latestJSVersion", JSVersionChanged)
WORKER_PREF("intl.accept_languages", PrefLanguagesChanged) WORKER_PREF("intl.accept_languages", PrefLanguagesChanged)
WORKER_PREF("general.appname.override", AppNameOverrideChanged) WORKER_PREF("general.appname.override", AppNameOverrideChanged)