зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1602483 part 2. Add a window id argument to CheckLoadURIWithPrincipal. r=ckerschb
Differential Revision: https://phabricator.services.mozilla.com/D56428 --HG-- rename : devtools/client/webconsole/test/browser/browser_webconsole_same_origin_errors.js => devtools/client/webconsole/test/browser/browser_webconsole_checkloaduri_errors.js rename : devtools/client/webconsole/test/browser/test-same-origin-required-load.html => devtools/client/webconsole/test/browser/test-checkloaduri-failure.html extra : moz-landing-system : lando
This commit is contained in:
Родитель
c0594d0833
Коммит
ee1cc488f2
|
@ -108,10 +108,15 @@ interface nsIScriptSecurityManager : nsISupports
|
|||
* @param aPrincipal the principal identifying the actor causing the load
|
||||
* @param uri the URI that is being loaded
|
||||
* @param flags the permission set, see above
|
||||
* @param innerWindowID the window ID for error reporting. If this is 0
|
||||
* (which happens automatically if it's not passed from JS), errors
|
||||
* will only appear in the browser console, not window-associated
|
||||
* consoles like the web console.
|
||||
*/
|
||||
void checkLoadURIWithPrincipal(in nsIPrincipal aPrincipal,
|
||||
in nsIURI uri,
|
||||
in unsigned long flags);
|
||||
in unsigned long flags,
|
||||
[optional] in unsigned long long innerWindowID);
|
||||
|
||||
/**
|
||||
* Similar to checkLoadURIWithPrincipal but there are two differences:
|
||||
|
|
|
@ -518,8 +518,10 @@ nsScriptSecurityManager::CheckLoadURIFromScript(JSContext* cx, nsIURI* aURI) {
|
|||
// Get principal of currently executing script.
|
||||
MOZ_ASSERT(cx == nsContentUtils::GetCurrentJSContext());
|
||||
nsIPrincipal* principal = nsContentUtils::SubjectPrincipal();
|
||||
nsresult rv = CheckLoadURIWithPrincipal(principal, aURI,
|
||||
nsIScriptSecurityManager::STANDARD);
|
||||
nsresult rv = CheckLoadURIWithPrincipal(
|
||||
// Passing 0 for the window ID here is OK, because we will report a
|
||||
// script-visible exception anyway.
|
||||
principal, aURI, nsIScriptSecurityManager::STANDARD, 0);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
// OK to load
|
||||
return NS_OK;
|
||||
|
@ -584,7 +586,8 @@ static bool EqualOrSubdomain(nsIURI* aProbeArg, nsIURI* aBase) {
|
|||
NS_IMETHODIMP
|
||||
nsScriptSecurityManager::CheckLoadURIWithPrincipal(nsIPrincipal* aPrincipal,
|
||||
nsIURI* aTargetURI,
|
||||
uint32_t aFlags) {
|
||||
uint32_t aFlags,
|
||||
uint64_t aInnerWindowID) {
|
||||
MOZ_ASSERT(aPrincipal, "CheckLoadURIWithPrincipal must have a principal");
|
||||
|
||||
// If someone passes a flag that we don't understand, we should
|
||||
|
@ -622,7 +625,8 @@ nsScriptSecurityManager::CheckLoadURIWithPrincipal(nsIPrincipal* aPrincipal,
|
|||
if (basePrin->Is<ExpandedPrincipal>()) {
|
||||
auto expanded = basePrin->As<ExpandedPrincipal>();
|
||||
for (auto& prin : expanded->AllowList()) {
|
||||
nsresult rv = CheckLoadURIWithPrincipal(prin, aTargetURI, aFlags);
|
||||
nsresult rv =
|
||||
CheckLoadURIWithPrincipal(prin, aTargetURI, aFlags, aInnerWindowID);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
// Allow access if it succeeded with one of the allowlisted principals
|
||||
return NS_OK;
|
||||
|
@ -673,11 +677,15 @@ nsScriptSecurityManager::CheckLoadURIWithPrincipal(nsIPrincipal* aPrincipal,
|
|||
// access:
|
||||
rv = CheckLoadURIFlags(
|
||||
sourceURI, aTargetURI, sourceBaseURI, targetBaseURI, aFlags,
|
||||
aPrincipal->OriginAttributesRef().mPrivateBrowsingId > 0);
|
||||
aPrincipal->OriginAttributesRef().mPrivateBrowsingId > 0,
|
||||
aInnerWindowID);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
// Check the principal is allowed to load the target.
|
||||
// Unfortunately we don't have a window id to work with here...
|
||||
return aPrincipal->CheckMayLoadWithReporting(targetBaseURI, false, 0);
|
||||
if (aFlags & nsIScriptSecurityManager::DONT_REPORT_ERRORS) {
|
||||
return aPrincipal->CheckMayLoad(targetBaseURI, false);
|
||||
}
|
||||
return aPrincipal->CheckMayLoadWithReporting(targetBaseURI, false,
|
||||
aInnerWindowID);
|
||||
}
|
||||
|
||||
//-- get the source scheme
|
||||
|
@ -794,7 +802,8 @@ nsScriptSecurityManager::CheckLoadURIWithPrincipal(nsIPrincipal* aPrincipal,
|
|||
if (!schemesMatch || (denySameSchemeLinks && !isSamePage)) {
|
||||
return CheckLoadURIFlags(
|
||||
currentURI, currentOtherURI, sourceBaseURI, targetBaseURI, aFlags,
|
||||
aPrincipal->OriginAttributesRef().mPrivateBrowsingId > 0);
|
||||
aPrincipal->OriginAttributesRef().mPrivateBrowsingId > 0,
|
||||
aInnerWindowID);
|
||||
}
|
||||
// Otherwise... check if we can nest another level:
|
||||
nsCOMPtr<nsINestedURI> nestedURI = do_QueryInterface(currentURI);
|
||||
|
@ -828,7 +837,8 @@ nsScriptSecurityManager::CheckLoadURIWithPrincipal(nsIPrincipal* aPrincipal,
|
|||
*/
|
||||
nsresult nsScriptSecurityManager::CheckLoadURIFlags(
|
||||
nsIURI* aSourceURI, nsIURI* aTargetURI, nsIURI* aSourceBaseURI,
|
||||
nsIURI* aTargetBaseURI, uint32_t aFlags, bool aFromPrivateWindow) {
|
||||
nsIURI* aTargetBaseURI, uint32_t aFlags, bool aFromPrivateWindow,
|
||||
uint64_t aInnerWindowID) {
|
||||
// Note that the order of policy checks here is very important!
|
||||
// We start from most restrictive and work our way down.
|
||||
bool reportErrors = !(aFlags & nsIScriptSecurityManager::DONT_REPORT_ERRORS);
|
||||
|
@ -844,7 +854,8 @@ nsresult nsScriptSecurityManager::CheckLoadURIFlags(
|
|||
if (NS_FAILED(rv)) {
|
||||
// Deny access, since the origin principal is not system
|
||||
if (reportErrors) {
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow);
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow,
|
||||
aInnerWindowID);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
@ -856,7 +867,8 @@ nsresult nsScriptSecurityManager::CheckLoadURIFlags(
|
|||
aTargetURI, nsIProtocolHandler::URI_DISALLOW_IN_PRIVATE_CONTEXT);
|
||||
if (NS_FAILED(rv)) {
|
||||
if (reportErrors) {
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow);
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow,
|
||||
aInnerWindowID);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
@ -923,7 +935,8 @@ nsresult nsScriptSecurityManager::CheckLoadURIFlags(
|
|||
}
|
||||
|
||||
if (reportErrors) {
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow);
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow,
|
||||
aInnerWindowID);
|
||||
}
|
||||
return NS_ERROR_DOM_BAD_URI;
|
||||
}
|
||||
|
@ -948,7 +961,8 @@ nsresult nsScriptSecurityManager::CheckLoadURIFlags(
|
|||
|
||||
// Nothing else.
|
||||
if (reportErrors) {
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow);
|
||||
ReportError(errorTag, aSourceURI, aTargetURI, aFromPrivateWindow,
|
||||
aInnerWindowID);
|
||||
}
|
||||
return NS_ERROR_DOM_BAD_URI;
|
||||
}
|
||||
|
@ -1050,7 +1064,7 @@ nsScriptSecurityManager::CheckLoadURIStrWithPrincipal(
|
|||
rv = NS_NewURI(getter_AddRefs(target), aTargetURIStr);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
rv = CheckLoadURIWithPrincipal(aPrincipal, target, aFlags);
|
||||
rv = CheckLoadURIWithPrincipal(aPrincipal, target, aFlags, 0);
|
||||
if (rv == NS_ERROR_DOM_BAD_URI) {
|
||||
// Don't warn because NS_ERROR_DOM_BAD_URI is one of the expected
|
||||
// return values.
|
||||
|
@ -1082,7 +1096,7 @@ nsScriptSecurityManager::CheckLoadURIStrWithPrincipal(
|
|||
getter_AddRefs(target));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
rv = CheckLoadURIWithPrincipal(aPrincipal, target, aFlags);
|
||||
rv = CheckLoadURIWithPrincipal(aPrincipal, target, aFlags, 0);
|
||||
if (rv == NS_ERROR_DOM_BAD_URI) {
|
||||
// Don't warn because NS_ERROR_DOM_BAD_URI is one of the expected
|
||||
// return values.
|
||||
|
|
|
@ -102,7 +102,8 @@ class nsScriptSecurityManager final : public nsIScriptSecurityManager {
|
|||
|
||||
nsresult CheckLoadURIFlags(nsIURI* aSourceURI, nsIURI* aTargetURI,
|
||||
nsIURI* aSourceBaseURI, nsIURI* aTargetBaseURI,
|
||||
uint32_t aFlags, bool aFromPrivateWindow);
|
||||
uint32_t aFlags, bool aFromPrivateWindow,
|
||||
uint64_t aInnerWindowID);
|
||||
|
||||
// Returns the file URI allowlist, initializing it if it has not been
|
||||
// initialized.
|
||||
|
|
|
@ -40,6 +40,7 @@ support-files =
|
|||
test-iframe-child.html
|
||||
test-iframe-parent.html
|
||||
test-certificate-messages.html
|
||||
test-checkloaduri-failure.html
|
||||
test-click-function-to-source.html
|
||||
test-click-function-to-source.js
|
||||
test-click-function-to-mapped-source.html
|
||||
|
@ -309,6 +310,7 @@ tags = mcb
|
|||
[browser_webconsole_cd_iframe.js]
|
||||
[browser_webconsole_certificate_messages.js]
|
||||
skip-if = fission
|
||||
[browser_webconsole_checkloaduri_errors.js]
|
||||
[browser_webconsole_clear_cache.js]
|
||||
[browser_webconsole_click_function_to_source.js]
|
||||
[browser_webconsole_click_function_to_mapped_source.js]
|
||||
|
|
|
@ -0,0 +1,29 @@
|
|||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
// Ensure that same-origin errors are logged to the console.
|
||||
|
||||
"use strict";
|
||||
|
||||
const TEST_URI =
|
||||
"http://example.com/browser/devtools/client/webconsole/test/browser/test-checkloaduri-failure.html";
|
||||
|
||||
add_task(async function() {
|
||||
const hud = await openNewTabAndConsole(TEST_URI);
|
||||
|
||||
const targetURL = "file:///something-weird";
|
||||
const onErrorMessage = waitForMessage(hud, "may not load or link");
|
||||
SpecialPowers.spawn(gBrowser.selectedBrowser, [targetURL], url => {
|
||||
XPCNativeWrapper.unwrap(content).testImage(url);
|
||||
});
|
||||
const message = await onErrorMessage;
|
||||
const node = message.node;
|
||||
ok(
|
||||
node.classList.contains("error"),
|
||||
"The message has the expected classname"
|
||||
);
|
||||
ok(
|
||||
node.textContent.includes(targetURL),
|
||||
"The message is about the thing we were expecting"
|
||||
);
|
||||
});
|
|
@ -0,0 +1,23 @@
|
|||
<!-- This Source Code Form is subject to the terms of the Mozilla Public
|
||||
- License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
- file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
|
||||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Test loads that fail checkLoadURI</title>
|
||||
<script>
|
||||
/* exported testImage */
|
||||
"use strict";
|
||||
|
||||
function testImage(url) {
|
||||
const body = document.body;
|
||||
const image = new Image();
|
||||
image.src = url;
|
||||
body.append(image);
|
||||
}
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
</body>
|
||||
</html>
|
|
@ -5676,7 +5676,8 @@ nsresult nsDocShell::SetupRefreshURIFromHeader(nsIURI* aBaseURI,
|
|||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = securityManager->CheckLoadURIWithPrincipal(
|
||||
aPrincipal, uri,
|
||||
nsIScriptSecurityManager::LOAD_IS_AUTOMATIC_DOCUMENT_REPLACEMENT);
|
||||
nsIScriptSecurityManager::LOAD_IS_AUTOMATIC_DOCUMENT_REPLACEMENT,
|
||||
aInnerWindowID);
|
||||
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
bool isjs = true;
|
||||
|
|
|
@ -39,9 +39,12 @@ already_AddRefed<nsDocShellLoadState> LocationBase::CheckURL(
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
// Check to see if URI is allowed.
|
||||
// Check to see if URI is allowed. We're not going to worry about a
|
||||
// window ID here because it's not 100% clear which window's id we
|
||||
// would want, and we're throwing a content-visible exception
|
||||
// anyway.
|
||||
nsresult rv = ssm->CheckLoadURIWithPrincipal(
|
||||
&aSubjectPrincipal, aURI, nsIScriptSecurityManager::STANDARD);
|
||||
&aSubjectPrincipal, aURI, nsIScriptSecurityManager::STANDARD, 0);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
nsAutoCString spec;
|
||||
aURI->GetSpec(spec);
|
||||
|
|
|
@ -3160,7 +3160,8 @@ bool nsContentUtils::CanLoadImage(nsIURI* aURI, nsINode* aNode,
|
|||
// from anywhere. This allows editor to insert images from file://
|
||||
// into documents that are being edited.
|
||||
rv = sSecurityManager->CheckLoadURIWithPrincipal(
|
||||
aLoadingPrincipal, aURI, nsIScriptSecurityManager::ALLOW_CHROME);
|
||||
aLoadingPrincipal, aURI, nsIScriptSecurityManager::ALLOW_CHROME,
|
||||
aLoadingDocument->InnerWindowID());
|
||||
if (NS_FAILED(rv)) {
|
||||
return false;
|
||||
}
|
||||
|
@ -5100,7 +5101,8 @@ void nsContentUtils::TriggerLink(nsIContent* aContent, nsIURI* aLinkURI,
|
|||
if (sSecurityManager) {
|
||||
uint32_t flag = static_cast<uint32_t>(nsIScriptSecurityManager::STANDARD);
|
||||
proceed = sSecurityManager->CheckLoadURIWithPrincipal(
|
||||
aContent->NodePrincipal(), aLinkURI, flag);
|
||||
aContent->NodePrincipal(), aLinkURI, flag,
|
||||
aContent->OwnerDoc()->InnerWindowID());
|
||||
}
|
||||
|
||||
// Only pass off the click event if the script security manager says it's ok.
|
||||
|
|
|
@ -693,7 +693,8 @@ nsresult nsFrameLoader::CheckURILoad(nsIURI* aURI,
|
|||
|
||||
// Check if we are allowed to load absURL
|
||||
nsresult rv = secMan->CheckLoadURIWithPrincipal(
|
||||
principal, aURI, nsIScriptSecurityManager::STANDARD);
|
||||
principal, aURI, nsIScriptSecurityManager::STANDARD,
|
||||
mOwnerContent->OwnerDoc()->InnerWindowID());
|
||||
if (NS_FAILED(rv)) {
|
||||
return rv; // We're not
|
||||
}
|
||||
|
|
|
@ -1251,10 +1251,11 @@ bool nsTreeSanitizer::SanitizeURL(mozilla::dom::Element* aElement,
|
|||
// in case someone goofs with these in the future, let's drop them.
|
||||
rv = NS_ERROR_FAILURE;
|
||||
} else {
|
||||
rv = secMan->CheckLoadURIWithPrincipal(sNullPrincipal, attrURI, flags);
|
||||
rv = secMan->CheckLoadURIWithPrincipal(sNullPrincipal, attrURI, flags,
|
||||
0);
|
||||
}
|
||||
} else {
|
||||
rv = secMan->CheckLoadURIWithPrincipal(sNullPrincipal, attrURI, flags);
|
||||
rv = secMan->CheckLoadURIWithPrincipal(sNullPrincipal, attrURI, flags, 0);
|
||||
}
|
||||
}
|
||||
if (NS_FAILED(rv)) {
|
||||
|
|
|
@ -1659,7 +1659,8 @@ nsresult HTMLFormElement::GetActionURL(nsIURI** aActionURL,
|
|||
nsIScriptSecurityManager* securityManager =
|
||||
nsContentUtils::GetSecurityManager();
|
||||
rv = securityManager->CheckLoadURIWithPrincipal(
|
||||
NodePrincipal(), actionURL, nsIScriptSecurityManager::STANDARD);
|
||||
NodePrincipal(), actionURL, nsIScriptSecurityManager::STANDARD,
|
||||
OwnerDoc()->InnerWindowID());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
// Potentially the page uses the CSP directive 'upgrade-insecure-requests'. In
|
||||
|
|
|
@ -309,7 +309,8 @@ static nsresult DoCheckLoadURIChecks(nsIURI* aURI, nsILoadInfo* aLoadInfo) {
|
|||
// the LoadingPrincipal when SEC_ALLOW_CROSS_ORIGIN_* security flags are set,
|
||||
// to allow, e.g. user stylesheets to load chrome:// URIs.
|
||||
return nsContentUtils::GetSecurityManager()->CheckLoadURIWithPrincipal(
|
||||
aLoadInfo->TriggeringPrincipal(), aURI, aLoadInfo->CheckLoadURIFlags());
|
||||
aLoadInfo->TriggeringPrincipal(), aURI, aLoadInfo->CheckLoadURIFlags(),
|
||||
aLoadInfo->GetInnerWindowID());
|
||||
}
|
||||
|
||||
static bool URIHasFlags(nsIURI* aURI, uint32_t aURIFlags) {
|
||||
|
@ -955,7 +956,7 @@ nsContentSecurityManager::AsyncOnChannelRedirect(
|
|||
nsIScriptSecurityManager::LOAD_IS_AUTOMATIC_DOCUMENT_REPLACEMENT |
|
||||
nsIScriptSecurityManager::DISALLOW_SCRIPT;
|
||||
rv = nsContentUtils::GetSecurityManager()->CheckLoadURIWithPrincipal(
|
||||
oldPrincipal, newURI, flags);
|
||||
oldPrincipal, newURI, flags, loadInfo->GetInnerWindowID());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
aCb->OnRedirectVerifyCallback(NS_OK);
|
||||
|
|
|
@ -685,8 +685,9 @@ nsresult nsXMLContentSink::MaybeProcessXSLTLink(
|
|||
|
||||
// Do security check
|
||||
nsIScriptSecurityManager* secMan = nsContentUtils::GetSecurityManager();
|
||||
rv = secMan->CheckLoadURIWithPrincipal(
|
||||
mDocument->NodePrincipal(), url, nsIScriptSecurityManager::ALLOW_CHROME);
|
||||
rv = secMan->CheckLoadURIWithPrincipal(mDocument->NodePrincipal(), url,
|
||||
nsIScriptSecurityManager::ALLOW_CHROME,
|
||||
mDocument->InnerWindowID());
|
||||
NS_ENSURE_SUCCESS(rv, NS_OK);
|
||||
|
||||
nsCOMPtr<nsILoadInfo> secCheckLoadInfo =
|
||||
|
|
|
@ -759,7 +759,7 @@ nsresult XULContentSinkImpl::OpenScript(const char16_t** aAttributes,
|
|||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = mSecMan->CheckLoadURIWithPrincipal(
|
||||
doc->NodePrincipal(), script->mSrcURI,
|
||||
nsIScriptSecurityManager::ALLOW_CHROME);
|
||||
nsIScriptSecurityManager::ALLOW_CHROME, doc->InnerWindowID());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -904,12 +904,12 @@ nsresult nsCORSListenerProxy::UpdateChannel(nsIChannel* aChannel,
|
|||
// Check that the uri is ok to load
|
||||
uint32_t flags = loadInfo->CheckLoadURIFlags();
|
||||
rv = nsContentUtils::GetSecurityManager()->CheckLoadURIWithPrincipal(
|
||||
mRequestingPrincipal, uri, flags);
|
||||
mRequestingPrincipal, uri, flags, loadInfo->GetInnerWindowID());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
if (originalURI != uri) {
|
||||
rv = nsContentUtils::GetSecurityManager()->CheckLoadURIWithPrincipal(
|
||||
mRequestingPrincipal, originalURI, flags);
|
||||
mRequestingPrincipal, originalURI, flags, loadInfo->GetInnerWindowID());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче