Skip to content

Commit 1f5d422

Browse files
Bug 1991135, part 1 - Add support for <meta name=rating> behind a pref - r=dom-core,firefox-desktop-core-reviewers ,fluent-reviewers,bolsson,smaug,frontend-codestyle-reviewers,Gijs
Differential Revision: https://phabricator.services.mozilla.com/D266422
1 parent eb27707 commit 1f5d422

25 files changed

+309
-1
lines changed

docshell/base/BrowsingContext.cpp

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -489,6 +489,18 @@ already_AddRefed<BrowsingContext> BrowsingContext::CreateDetached(
489489
? inherit->GetIPAddressSpace()
490490
: nsILoadInfo::IPAddressSpace::Unknown;
491491

492+
bool parentalControlsEnabled;
493+
if (inherit) {
494+
parentalControlsEnabled = inherit->GetParentalControlsEnabled();
495+
} else if (XRE_IsParentProcess()) {
496+
parentalControlsEnabled =
497+
CanonicalBrowsingContext::ShouldEnforceParentalControls();
498+
} else {
499+
parentalControlsEnabled = false;
500+
}
501+
502+
fields.Get<IDX_ParentalControlsEnabled>() = parentalControlsEnabled;
503+
492504
fields.Get<IDX_IsPopupRequested>() = aOptions.isPopupRequested;
493505

494506
fields.Get<IDX_TopLevelCreatedByWebContent>() =

docshell/base/BrowsingContext.h

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,7 +284,10 @@ struct EmbedderColorSchemes {
284284
* protections */ \
285285
FIELD(TopInnerSizeForRFP, CSSIntSize) \
286286
/* Used to propagate document's IPAddressSpace */ \
287-
FIELD(IPAddressSpace, nsILoadInfo::IPAddressSpace)
287+
FIELD(IPAddressSpace, nsILoadInfo::IPAddressSpace) \
288+
/* This is true if we should redirect to an error page when inserting * \
289+
* meta tags flagging adult content into our documents */ \
290+
FIELD(ParentalControlsEnabled, bool)
288291

289292
// BrowsingContext, in this context, is the cross process replicated
290293
// environment in which information about documents is stored. In
@@ -1420,6 +1423,10 @@ class BrowsingContext : public nsILoadContext, public nsWrapperCache {
14201423
return XRE_IsParentProcess();
14211424
}
14221425

1426+
bool CanSet(FieldIndex<IDX_ParentalControlsEnabled>, bool, ContentParent*) {
1427+
return XRE_IsParentProcess();
1428+
}
1429+
14231430
// Overload `DidSet` to get notifications for a particular field being set.
14241431
//
14251432
// You can also overload the variant that gets the old value if you need it.

docshell/base/CanonicalBrowsingContext.cpp

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,8 +41,10 @@
4141
#include "mozilla/StaticPrefs_browser.h"
4242
#include "mozilla/StaticPrefs_docshell.h"
4343
#include "mozilla/StaticPrefs_fission.h"
44+
#include "mozilla/StaticPrefs_security.h"
4445
#include "mozilla/glean/DomMetrics.h"
4546
#include "nsILayoutHistoryState.h"
47+
#include "nsIParentalControlsService.h"
4648
#include "nsIPrintSettings.h"
4749
#include "nsIPrintSettingsService.h"
4850
#include "nsISupports.h"
@@ -271,6 +273,7 @@ void CanonicalBrowsingContext::ReplacedBy(
271273
txn.SetForceOffline(GetForceOffline());
272274
txn.SetTopInnerSizeForRFP(GetTopInnerSizeForRFP());
273275
txn.SetIPAddressSpace(GetIPAddressSpace());
276+
txn.SetParentalControlsEnabled(GetParentalControlsEnabled());
274277

275278
if (!GetLanguageOverride().IsEmpty()) {
276279
// Reapply language override to update the corresponding realm.
@@ -3693,6 +3696,23 @@ bool CanonicalBrowsingContext::CanOpenModalPicker() {
36933696
return true;
36943697
}
36953698

3699+
bool CanonicalBrowsingContext::ShouldEnforceParentalControls() {
3700+
if (StaticPrefs::security_restrict_to_adults_always()) {
3701+
return true;
3702+
}
3703+
if (StaticPrefs::security_restrict_to_adults_respect_platform()) {
3704+
bool enabled;
3705+
nsCOMPtr<nsIParentalControlsService> pcs =
3706+
do_CreateInstance("@mozilla.org/parental-controls-service;1");
3707+
nsresult rv = pcs->GetParentalControlsEnabled(&enabled);
3708+
if (NS_FAILED(rv)) {
3709+
return false;
3710+
}
3711+
return enabled;
3712+
}
3713+
return false;
3714+
}
3715+
36963716
NS_IMPL_CYCLE_COLLECTION_CLASS(CanonicalBrowsingContext)
36973717

36983718
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(CanonicalBrowsingContext,

docshell/base/CanonicalBrowsingContext.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -453,6 +453,8 @@ class CanonicalBrowsingContext final : public BrowsingContext {
453453

454454
bool CanOpenModalPicker();
455455

456+
static bool ShouldEnforceParentalControls();
457+
456458
protected:
457459
// Called when the browsing context is being discarded.
458460
void CanonicalDiscard();

docshell/base/nsAboutRedirector.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -175,6 +175,10 @@ static const RedirEntry kRedirMap[] = {
175175
nsIAboutModule::HIDE_FROM_ABOUTABOUT},
176176
{"processes", "chrome://global/content/aboutProcesses.html",
177177
nsIAboutModule::ALLOW_SCRIPT | nsIAboutModule::IS_SECURE_CHROME_UI},
178+
{"restricted", "chrome://global/content/aboutRestricted/aboutRestricted.html",
179+
nsIAboutModule::URI_SAFE_FOR_UNTRUSTED_CONTENT |
180+
nsIAboutModule::URI_CAN_LOAD_IN_CHILD | nsIAboutModule::ALLOW_SCRIPT |
181+
nsIAboutModule::HIDE_FROM_ABOUTABOUT},
178182
// about:serviceworkers always wants to load in the parent process because
179183
// the only place nsIServiceWorkerManager has any data is in the parent
180184
// process.

docshell/base/nsDocShell.cpp

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3566,6 +3566,12 @@ nsDocShell::DisplayLoadError(nsresult aError, nsIURI* aURI,
35663566
if (messageStr.IsEmpty()) {
35673567
messageStr.AssignLiteral(u" ");
35683568
}
3569+
} else if (aError == NS_ERROR_RESTRICTED_CONTENT) {
3570+
errorPage.AssignLiteral("restricted");
3571+
error = "restrictedcontent";
3572+
if (messageStr.IsEmpty()) {
3573+
messageStr.AssignLiteral(u" ");
3574+
}
35693575
} else {
35703576
// Errors requiring simple formatting
35713577
switch (aError) {
@@ -4117,6 +4123,17 @@ nsresult nsDocShell::ReloadNavigable(
41174123
return ReloadDocument(this, doc, loadType, bc, currentURI, referrerInfo);
41184124
}
41194125

4126+
void nsDocShell::DisplayRestrictedContentError() {
4127+
bool didDisplayLoadError = false;
4128+
RefPtr<mozilla::dom::Document> doc = GetDocument();
4129+
if (!doc) {
4130+
return;
4131+
}
4132+
doc->TerminateParserAndDisableScripts();
4133+
DisplayLoadError(NS_ERROR_RESTRICTED_CONTENT, doc->GetDocumentURI(), nullptr, nullptr,
4134+
&didDisplayLoadError);
4135+
}
4136+
41204137
/* static */
41214138
nsresult nsDocShell::ReloadDocument(nsDocShell* aDocShell, Document* aDocument,
41224139
uint32_t aLoadType,

docshell/base/nsDocShell.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -782,6 +782,11 @@ class nsDocShell final : public nsDocLoader,
782782
return didDisplayLoadError;
783783
}
784784

785+
// Called when a document is recognised as content the device owner doesn't
786+
// want to be displayed. Stops parsing, stops scripts, and displays an
787+
// error page with DisplayLoadError.
788+
void DisplayRestrictedContentError();
789+
785790
//
786791
// Uncategorized
787792
//

docshell/build/components.conf

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ about_pages = [
2626
'networking',
2727
'performance',
2828
'processes',
29+
'restricted',
2930
'serviceworkers',
3031
'srcdoc',
3132
'support',

dom/base/Document.cpp

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -384,6 +384,7 @@
384384
#include "nsINodeList.h"
385385
#include "nsIObjectLoadingContent.h"
386386
#include "nsIObserverService.h"
387+
#include "nsIParentalControlsService.h"
387388
#include "nsIPermission.h"
388389
#include "nsIPrompt.h"
389390
#include "nsIPropertyBag2.h"
@@ -11857,6 +11858,34 @@ void Document::ProcessMETATag(HTMLMetaElement* aMetaElement) {
1185711858
SetHeaderData(nsGkAtoms::handheldFriendly, result);
1185811859
}
1185911860
}
11861+
// Check for Restricted To Adults meta tag
11862+
if (aMetaElement->AttrValueIs(kNameSpaceID_None, nsGkAtoms::name,
11863+
nsGkAtoms::rating, eIgnoreCase)) {
11864+
if (aMetaElement->AttrValueIs(kNameSpaceID_None, nsGkAtoms::content,
11865+
nsGkAtoms::adult, eIgnoreCase) ||
11866+
aMetaElement->AttrValueIs(kNameSpaceID_None, nsGkAtoms::content,
11867+
nsGkAtoms::restrictToAdults, eIgnoreCase)) {
11868+
BrowsingContext* bc = GetBrowsingContext();
11869+
if (bc && bc->GetParentalControlsEnabled() && GetDocShell()) {
11870+
RefPtr<nsDocShell> docShell = nsDocShell::Cast(GetDocShell());
11871+
nsCOMPtr<nsIRunnable> redirect = NewRunnableMethod(
11872+
"Document::ProcessMETATag::DisplayRestrictedContentError", docShell,
11873+
&nsDocShell::DisplayRestrictedContentError);
11874+
nsContentUtils::AddScriptRunner(redirect.forget());
11875+
}
11876+
}
11877+
}
11878+
}
11879+
11880+
void Document::TerminateParserAndDisableScripts() {
11881+
if (mParser) {
11882+
Unused << mParser->Terminate();
11883+
MOZ_ASSERT(!mParser, "mParser should have been null'd out");
11884+
}
11885+
11886+
if (WindowContext* wc = GetWindowContext()) {
11887+
Unused << wc->SetAllowJavascript(false);
11888+
}
1186011889
}
1186111890

1186211891
already_AddRefed<Element> Document::CreateElem(const nsAString& aName,

dom/base/Document.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2241,6 +2241,9 @@ class Document : public nsINode,
22412241
}
22422242

22432243
void ProcessMETATag(HTMLMetaElement* aMetaElement);
2244+
2245+
void TerminateParserAndDisableScripts();
2246+
22442247
/**
22452248
* Create an element with the specified name, prefix and namespace ID.
22462249
* Returns null if element name parsing failed.

0 commit comments

Comments
 (0)