gecko-dev/dom/clients/manager/ClientValidation.cpp
Kristen Wright 5094f72a18 Bug 1622111 - Convert security.data_uri.unique_opaque_origin to static pref and remove ClientPrefs. r=njn
Converts security.data_uri.unique_opaque_origin to a static pref. This pref was initialized by the ClientManager in ClientPrefs, so this commit also removes those files. Somehow this pref was getting added in VarCache twice, so it also removes the places where the pref was added in Networking.

Differential Revision: https://phabricator.services.mozilla.com/D67185

--HG--
extra : moz-landing-system : lando
2020-03-23 16:08:52 +00:00

160 lines
5.7 KiB
C++

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* 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/. */
#include "ClientValidation.h"
#include "mozilla/StaticPrefs_security.h"
#include "mozilla/net/MozURL.h"
namespace mozilla {
namespace dom {
using mozilla::ipc::ContentPrincipalInfo;
using mozilla::ipc::PrincipalInfo;
using mozilla::net::MozURL;
bool ClientIsValidPrincipalInfo(const PrincipalInfo& aPrincipalInfo) {
// Ideally we would verify that the source process has permission to
// create a window or worker with the given principal, but we don't
// currently have any such restriction in place. Instead, at least
// verify the PrincipalInfo is an expected type and has a parsable
// origin/spec.
switch (aPrincipalInfo.type()) {
// Any system and null principal is acceptable.
case PrincipalInfo::TSystemPrincipalInfo:
case PrincipalInfo::TNullPrincipalInfo: {
return true;
}
// Validate content principals to ensure that the origin and spec are sane.
case PrincipalInfo::TContentPrincipalInfo: {
const ContentPrincipalInfo& content =
aPrincipalInfo.get_ContentPrincipalInfo();
// Verify the principal spec parses.
RefPtr<MozURL> specURL;
nsresult rv = MozURL::Init(getter_AddRefs(specURL), content.spec());
NS_ENSURE_SUCCESS(rv, false);
// Verify the principal originNoSuffix parses.
RefPtr<MozURL> originURL;
rv = MozURL::Init(getter_AddRefs(originURL), content.originNoSuffix());
NS_ENSURE_SUCCESS(rv, false);
nsAutoCString originOrigin;
originURL->Origin(originOrigin);
nsAutoCString specOrigin;
specURL->Origin(specOrigin);
// For now require Clients to have a principal where both its
// originNoSuffix and spec have the same origin. This will
// exclude a variety of unusual combinations within the browser
// but its adequate for the features need to support right now.
// If necessary we could expand this function to handle more
// cases in the future.
return specOrigin == originOrigin;
}
default: {
break;
}
}
// Windows and workers should not have expanded URLs, etc.
return false;
}
bool ClientIsValidCreationURL(const PrincipalInfo& aPrincipalInfo,
const nsACString& aURL) {
RefPtr<MozURL> url;
nsresult rv = MozURL::Init(getter_AddRefs(url), aURL);
NS_ENSURE_SUCCESS(rv, false);
switch (aPrincipalInfo.type()) {
case PrincipalInfo::TContentPrincipalInfo: {
// Any origin can create an about:blank or about:srcdoc Client.
if (aURL.LowerCaseEqualsLiteral("about:blank") ||
aURL.LowerCaseEqualsLiteral("about:srcdoc")) {
return true;
}
const ContentPrincipalInfo& content =
aPrincipalInfo.get_ContentPrincipalInfo();
// Parse the principal origin URL as well. This ensures any MozURL
// parser issues effect both URLs equally.
RefPtr<MozURL> principalURL;
rv = MozURL::Init(getter_AddRefs(principalURL), content.originNoSuffix());
NS_ENSURE_SUCCESS(rv, false);
nsAutoCString origin;
url->Origin(origin);
nsAutoCString principalOrigin;
principalURL->Origin(principalOrigin);
// The vast majority of sites should simply result in the same principal
// and URL origin.
if (principalOrigin == origin) {
return true;
}
nsDependentCSubstring scheme = url->Scheme();
// Generally any origin can also open javascript: windows and workers.
if (scheme.LowerCaseEqualsLiteral("javascript")) {
return true;
}
// We have some tests that use data: URL windows without an opaque
// origin. This should only happen when a pref is set.
if (!StaticPrefs::security_data_uri_unique_opaque_origin() &&
scheme.LowerCaseEqualsLiteral("data")) {
return true;
}
// Otherwise don't support this URL type in the clients sub-system for
// now. This will exclude a variety of internal browser clients, but
// currently we don't need to support those. This function can be
// expanded to handle more cases as necessary.
return false;
}
case PrincipalInfo::TSystemPrincipalInfo: {
nsDependentCSubstring scheme = url->Scheme();
// While many types of documents can be created with a system principal,
// there are only a few that can reasonably become windows. We attempt
// to validate the list of known cases here with a simple scheme check.
return scheme.LowerCaseEqualsLiteral("about") ||
scheme.LowerCaseEqualsLiteral("chrome") ||
scheme.LowerCaseEqualsLiteral("resource") ||
scheme.LowerCaseEqualsLiteral("blob") ||
scheme.LowerCaseEqualsLiteral("javascript") ||
scheme.LowerCaseEqualsLiteral("view-source") ||
(!StaticPrefs::security_data_uri_unique_opaque_origin() &&
scheme.LowerCaseEqualsLiteral("data"));
}
case PrincipalInfo::TNullPrincipalInfo: {
// A wide variety of clients can have a null principal. For example,
// sandboxed iframes can have a normal content URL. For now allow
// any parsable URL for null principals. This is relatively safe since
// null principals have unique origins and won't most ClientManagerService
// queries anyway.
return true;
}
default: {
break;
}
}
// Clients (windows/workers) should never have an expanded principal type.
return false;
}
} // namespace dom
} // namespace mozilla