aboutsummaryrefslogtreecommitdiffstats
path: root/components/script
diff options
context:
space:
mode:
Diffstat (limited to 'components/script')
-rw-r--r--components/script/dom/globalscope.rs11
-rw-r--r--components/script/dom/mod.rs5
-rw-r--r--components/script/dom/trustedhtml.rs45
-rw-r--r--components/script/dom/trustedscript.rs45
-rw-r--r--components/script/dom/trustedscripturl.rs45
-rw-r--r--components/script/dom/trustedtypepolicy.rs77
-rw-r--r--components/script/dom/trustedtypepolicyfactory.rs160
-rw-r--r--components/script/dom/window.rs8
-rw-r--r--components/script/dom/workerglobalscope.rs11
9 files changed, 407 insertions, 0 deletions
diff --git a/components/script/dom/globalscope.rs b/components/script/dom/globalscope.rs
index d0d7830e2bb..7d3c65dad2f 100644
--- a/components/script/dom/globalscope.rs
+++ b/components/script/dom/globalscope.rs
@@ -125,6 +125,7 @@ use crate::dom::promise::Promise;
use crate::dom::readablestream::ReadableStream;
use crate::dom::serviceworker::ServiceWorker;
use crate::dom::serviceworkerregistration::ServiceWorkerRegistration;
+use crate::dom::trustedtypepolicyfactory::TrustedTypePolicyFactory;
use crate::dom::underlyingsourcecontainer::UnderlyingSourceType;
#[cfg(feature = "webgpu")]
use crate::dom::webgpu::gpudevice::GPUDevice;
@@ -3300,6 +3301,16 @@ impl GlobalScope {
.borrow_mut()
.remove(&callback_id)
}
+
+ pub(crate) fn trusted_types(&self, can_gc: CanGc) -> DomRoot<TrustedTypePolicyFactory> {
+ if let Some(window) = self.downcast::<Window>() {
+ return window.TrustedTypes(can_gc);
+ }
+ if let Some(worker) = self.downcast::<WorkerGlobalScope>() {
+ return worker.TrustedTypes(can_gc);
+ }
+ unreachable!();
+ }
}
/// Returns the Rust global scope from a JS global object.
diff --git a/components/script/dom/mod.rs b/components/script/dom/mod.rs
index 0b32dafd4e1..417bcface58 100644
--- a/components/script/dom/mod.rs
+++ b/components/script/dom/mod.rs
@@ -575,6 +575,11 @@ pub(crate) mod touchlist;
pub(crate) mod trackevent;
pub(crate) mod transitionevent;
pub(crate) mod treewalker;
+pub(crate) mod trustedhtml;
+pub(crate) mod trustedscript;
+pub(crate) mod trustedscripturl;
+pub(crate) mod trustedtypepolicy;
+pub(crate) mod trustedtypepolicyfactory;
pub(crate) mod uievent;
pub(crate) mod underlyingsourcecontainer;
pub(crate) mod url;
diff --git a/components/script/dom/trustedhtml.rs b/components/script/dom/trustedhtml.rs
new file mode 100644
index 00000000000..07298601f2f
--- /dev/null
+++ b/components/script/dom/trustedhtml.rs
@@ -0,0 +1,45 @@
+/* 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 https://mozilla.org/MPL/2.0/. */
+
+use dom_struct::dom_struct;
+
+use crate::dom::bindings::codegen::Bindings::TrustedHTMLBinding::TrustedHTMLMethods;
+use crate::dom::bindings::reflector::{Reflector, reflect_dom_object};
+use crate::dom::bindings::root::DomRoot;
+use crate::dom::bindings::str::DOMString;
+use crate::dom::globalscope::GlobalScope;
+use crate::script_runtime::CanGc;
+
+#[dom_struct]
+pub struct TrustedHTML {
+ reflector_: Reflector,
+
+ data: String,
+}
+
+impl TrustedHTML {
+ fn new_inherited(data: String) -> Self {
+ Self {
+ reflector_: Reflector::new(),
+ data,
+ }
+ }
+
+ #[cfg_attr(crown, allow(crown::unrooted_must_root))]
+ pub(crate) fn new(data: String, global: &GlobalScope, can_gc: CanGc) -> DomRoot<Self> {
+ reflect_dom_object(Box::new(Self::new_inherited(data)), global, can_gc)
+ }
+}
+
+impl TrustedHTMLMethods<crate::DomTypeHolder> for TrustedHTML {
+ /// <https://www.w3.org/TR/trusted-types/#trustedhtml-stringification-behavior>
+ fn Stringifier(&self) -> DOMString {
+ DOMString::from(&*self.data)
+ }
+
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedhtml-tojson>
+ fn ToJSON(&self) -> DOMString {
+ DOMString::from(&*self.data)
+ }
+}
diff --git a/components/script/dom/trustedscript.rs b/components/script/dom/trustedscript.rs
new file mode 100644
index 00000000000..5ce51c24989
--- /dev/null
+++ b/components/script/dom/trustedscript.rs
@@ -0,0 +1,45 @@
+/* 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 https://mozilla.org/MPL/2.0/. */
+
+use dom_struct::dom_struct;
+
+use crate::dom::bindings::codegen::Bindings::TrustedScriptBinding::TrustedScriptMethods;
+use crate::dom::bindings::reflector::{Reflector, reflect_dom_object};
+use crate::dom::bindings::root::DomRoot;
+use crate::dom::bindings::str::DOMString;
+use crate::dom::globalscope::GlobalScope;
+use crate::script_runtime::CanGc;
+
+#[dom_struct]
+pub struct TrustedScript {
+ reflector_: Reflector,
+
+ data: String,
+}
+
+impl TrustedScript {
+ fn new_inherited(data: String) -> Self {
+ Self {
+ reflector_: Reflector::new(),
+ data,
+ }
+ }
+
+ #[cfg_attr(crown, allow(crown::unrooted_must_root))]
+ pub(crate) fn new(data: String, global: &GlobalScope, can_gc: CanGc) -> DomRoot<Self> {
+ reflect_dom_object(Box::new(Self::new_inherited(data)), global, can_gc)
+ }
+}
+
+impl TrustedScriptMethods<crate::DomTypeHolder> for TrustedScript {
+ /// <https://www.w3.org/TR/trusted-types/#trustedscript-stringification-behavior>
+ fn Stringifier(&self) -> DOMString {
+ DOMString::from(&*self.data)
+ }
+
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedscript-tojson>
+ fn ToJSON(&self) -> DOMString {
+ DOMString::from(&*self.data)
+ }
+}
diff --git a/components/script/dom/trustedscripturl.rs b/components/script/dom/trustedscripturl.rs
new file mode 100644
index 00000000000..01a82a4fff7
--- /dev/null
+++ b/components/script/dom/trustedscripturl.rs
@@ -0,0 +1,45 @@
+/* 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 https://mozilla.org/MPL/2.0/. */
+
+use dom_struct::dom_struct;
+
+use crate::dom::bindings::codegen::Bindings::TrustedScriptURLBinding::TrustedScriptURLMethods;
+use crate::dom::bindings::reflector::{Reflector, reflect_dom_object};
+use crate::dom::bindings::root::DomRoot;
+use crate::dom::bindings::str::DOMString;
+use crate::dom::globalscope::GlobalScope;
+use crate::script_runtime::CanGc;
+
+#[dom_struct]
+pub struct TrustedScriptURL {
+ reflector_: Reflector,
+
+ data: String,
+}
+
+impl TrustedScriptURL {
+ fn new_inherited(data: String) -> Self {
+ Self {
+ reflector_: Reflector::new(),
+ data,
+ }
+ }
+
+ #[cfg_attr(crown, allow(crown::unrooted_must_root))]
+ pub(crate) fn new(data: String, global: &GlobalScope, can_gc: CanGc) -> DomRoot<Self> {
+ reflect_dom_object(Box::new(Self::new_inherited(data)), global, can_gc)
+ }
+}
+
+impl TrustedScriptURLMethods<crate::DomTypeHolder> for TrustedScriptURL {
+ /// <https://www.w3.org/TR/trusted-types/#trustedscripturl-stringification-behavior>
+ fn Stringifier(&self) -> DOMString {
+ DOMString::from(&*self.data)
+ }
+
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedscripturl-tojson>
+ fn ToJSON(&self) -> DOMString {
+ DOMString::from(&*self.data)
+ }
+}
diff --git a/components/script/dom/trustedtypepolicy.rs b/components/script/dom/trustedtypepolicy.rs
new file mode 100644
index 00000000000..9cbeb25a83c
--- /dev/null
+++ b/components/script/dom/trustedtypepolicy.rs
@@ -0,0 +1,77 @@
+/* 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 https://mozilla.org/MPL/2.0/. */
+
+use dom_struct::dom_struct;
+use js::rust::HandleValue;
+
+use crate::dom::bindings::codegen::Bindings::TrustedTypePolicyBinding::TrustedTypePolicyMethods;
+use crate::dom::bindings::reflector::{DomGlobal, Reflector, reflect_dom_object};
+use crate::dom::bindings::root::DomRoot;
+use crate::dom::bindings::str::DOMString;
+use crate::dom::globalscope::GlobalScope;
+use crate::dom::trustedhtml::TrustedHTML;
+use crate::dom::trustedscript::TrustedScript;
+use crate::dom::trustedscripturl::TrustedScriptURL;
+use crate::script_runtime::{CanGc, JSContext};
+
+#[dom_struct]
+pub struct TrustedTypePolicy {
+ reflector_: Reflector,
+
+ name: String,
+}
+
+impl TrustedTypePolicy {
+ fn new_inherited(name: String) -> Self {
+ Self {
+ reflector_: Reflector::new(),
+ name,
+ }
+ }
+
+ #[cfg_attr(crown, allow(crown::unrooted_must_root))]
+ pub(crate) fn new(name: String, global: &GlobalScope, can_gc: CanGc) -> DomRoot<Self> {
+ reflect_dom_object(Box::new(Self::new_inherited(name)), global, can_gc)
+ }
+}
+
+impl TrustedTypePolicyMethods<crate::DomTypeHolder> for TrustedTypePolicy {
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicy-name>
+ fn Name(&self) -> DOMString {
+ DOMString::from(&*self.name)
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicy-createhtml>
+ fn CreateHTML(
+ &self,
+ _: JSContext,
+ data: DOMString,
+ _: Vec<HandleValue>,
+ can_gc: CanGc,
+ ) -> DomRoot<TrustedHTML> {
+ // TODO(36258): handle arguments
+ TrustedHTML::new(data.to_string(), &self.global(), can_gc)
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicy-createscript>
+ fn CreateScript(
+ &self,
+ _: JSContext,
+ data: DOMString,
+ _: Vec<HandleValue>,
+ can_gc: CanGc,
+ ) -> DomRoot<TrustedScript> {
+ // TODO(36258): handle arguments
+ TrustedScript::new(data.to_string(), &self.global(), can_gc)
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicy-createscripturl>
+ fn CreateScriptURL(
+ &self,
+ _: JSContext,
+ data: DOMString,
+ _: Vec<HandleValue>,
+ can_gc: CanGc,
+ ) -> DomRoot<TrustedScriptURL> {
+ // TODO(36258): handle arguments
+ TrustedScriptURL::new(data.to_string(), &self.global(), can_gc)
+ }
+}
diff --git a/components/script/dom/trustedtypepolicyfactory.rs b/components/script/dom/trustedtypepolicyfactory.rs
new file mode 100644
index 00000000000..02bafb021f1
--- /dev/null
+++ b/components/script/dom/trustedtypepolicyfactory.rs
@@ -0,0 +1,160 @@
+/* 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 https://mozilla.org/MPL/2.0/. */
+use std::cell::RefCell;
+
+use dom_struct::dom_struct;
+use js::rust::HandleValue;
+
+use crate::dom::bindings::codegen::Bindings::TrustedTypePolicyFactoryBinding::{
+ TrustedTypePolicyFactoryMethods, TrustedTypePolicyOptions,
+};
+use crate::dom::bindings::conversions::root_from_object;
+use crate::dom::bindings::error::{Error, Fallible};
+use crate::dom::bindings::reflector::{DomGlobal, Reflector, reflect_dom_object};
+use crate::dom::bindings::root::{DomRoot, MutNullableDom};
+use crate::dom::bindings::str::DOMString;
+use crate::dom::globalscope::GlobalScope;
+use crate::dom::trustedhtml::TrustedHTML;
+use crate::dom::trustedscript::TrustedScript;
+use crate::dom::trustedscripturl::TrustedScriptURL;
+use crate::dom::trustedtypepolicy::TrustedTypePolicy;
+use crate::script_runtime::{CanGc, JSContext};
+
+#[dom_struct]
+pub struct TrustedTypePolicyFactory {
+ reflector_: Reflector,
+
+ default_policy: MutNullableDom<TrustedTypePolicy>,
+ policy_names: RefCell<Vec<String>>,
+}
+
+impl TrustedTypePolicyFactory {
+ fn new_inherited() -> Self {
+ Self {
+ reflector_: Reflector::new(),
+ default_policy: Default::default(),
+ policy_names: RefCell::new(vec![]),
+ }
+ }
+
+ #[cfg_attr(crown, allow(crown::unrooted_must_root))]
+ pub(crate) fn new(global: &GlobalScope, can_gc: CanGc) -> DomRoot<Self> {
+ reflect_dom_object(Box::new(Self::new_inherited()), global, can_gc)
+ }
+
+ /// <https://www.w3.org/TR/trusted-types/#create-trusted-type-policy-algorithm>
+ fn create_trusted_type_policy(
+ &self,
+ policy_name: String,
+ _options: &TrustedTypePolicyOptions,
+ global: &GlobalScope,
+ can_gc: CanGc,
+ ) -> Fallible<DomRoot<TrustedTypePolicy>> {
+ // TODO(36258): implement proper CSP check
+ // Step 1: Let allowedByCSP be the result of executing Should Trusted Type policy creation be blocked by
+ // Content Security Policy? algorithm with global, policyName and factory’s created policy names value.
+ let allowed_by_csp = true;
+
+ // Step 2: If allowedByCSP is "Blocked", throw a TypeError and abort further steps.
+ if !allowed_by_csp {
+ return Err(Error::Type("Not allowed by CSP".to_string()));
+ }
+
+ // Step 3: If policyName is default and the factory’s default policy value is not null, throw a TypeError
+ // and abort further steps.
+ if policy_name == "default" && self.default_policy.get().is_some() {
+ return Err(Error::Type(
+ "Already set default policy for factory".to_string(),
+ ));
+ }
+
+ // Step 4: Let policy be a new TrustedTypePolicy object.
+ // Step 5: Set policy’s name property value to policyName.
+ let policy = TrustedTypePolicy::new(policy_name.clone(), global, can_gc);
+ // Step 6: Set policy’s options value to «[ "createHTML" ->
+ // options["createHTML", "createScript" -> options["createScript",
+ // "createScriptURL" -> options["createScriptURL" ]».
+ // TODO(36258): implement step 6
+ // Step 7: If the policyName is default, set the factory’s default policy value to policy.
+ if policy_name == "default" {
+ self.default_policy.set(Some(&policy))
+ }
+ // Step 8: Append policyName to factory’s created policy names.
+ self.policy_names.borrow_mut().push(policy_name);
+ // Step 9: Return policy.
+ Ok(policy)
+ }
+}
+
+impl TrustedTypePolicyFactoryMethods<crate::DomTypeHolder> for TrustedTypePolicyFactory {
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-createpolicy>
+ fn CreatePolicy(
+ &self,
+ policy_name: DOMString,
+ options: &TrustedTypePolicyOptions,
+ can_gc: CanGc,
+ ) -> Fallible<DomRoot<TrustedTypePolicy>> {
+ self.create_trusted_type_policy(policy_name.to_string(), options, &self.global(), can_gc)
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-ishtml>
+ #[allow(unsafe_code)]
+ fn IsHTML(&self, cx: JSContext, value: HandleValue) -> bool {
+ if !value.get().is_object() {
+ return false;
+ }
+ rooted!(in(*cx) let object = value.to_object());
+ unsafe { root_from_object::<TrustedHTML>(object.get(), *cx).is_ok() }
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-isscript>
+ #[allow(unsafe_code)]
+ fn IsScript(&self, cx: JSContext, value: HandleValue) -> bool {
+ if !value.get().is_object() {
+ return false;
+ }
+ rooted!(in(*cx) let object = value.to_object());
+ unsafe { root_from_object::<TrustedScript>(object.get(), *cx).is_ok() }
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-isscripturl>
+ #[allow(unsafe_code)]
+ fn IsScriptURL(&self, cx: JSContext, value: HandleValue) -> bool {
+ if !value.get().is_object() {
+ return false;
+ }
+ rooted!(in(*cx) let object = value.to_object());
+ unsafe { root_from_object::<TrustedScriptURL>(object.get(), *cx).is_ok() }
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-emptyhtml>
+ fn EmptyHTML(&self, can_gc: CanGc) -> DomRoot<TrustedHTML> {
+ TrustedHTML::new("".to_string(), &self.global(), can_gc)
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-emptyscript>
+ fn EmptyScript(&self, can_gc: CanGc) -> DomRoot<TrustedScript> {
+ TrustedScript::new("".to_string(), &self.global(), can_gc)
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-getattributetype>
+ fn GetAttributeType(
+ &self,
+ _: DOMString,
+ _: DOMString,
+ _: Option<DOMString>,
+ _: Option<DOMString>,
+ ) -> Option<DOMString> {
+ // TODO(36258): implement algorithm
+ Some(DOMString::from("".to_string()))
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-getpropertytype>
+ fn GetPropertyType(
+ &self,
+ _: DOMString,
+ _: DOMString,
+ _: Option<DOMString>,
+ ) -> Option<DOMString> {
+ // TODO(36258): implement algorithm
+ Some(DOMString::from("".to_string()))
+ }
+ /// <https://www.w3.org/TR/trusted-types/#dom-trustedtypepolicyfactory-defaultpolicy>
+ fn GetDefaultPolicy(&self) -> Option<DomRoot<TrustedTypePolicy>> {
+ self.default_policy.get()
+ }
+}
diff --git a/components/script/dom/window.rs b/components/script/dom/window.rs
index aff9d181081..fc9c4bf88d2 100644
--- a/components/script/dom/window.rs
+++ b/components/script/dom/window.rs
@@ -145,6 +145,7 @@ use crate::dom::selection::Selection;
use crate::dom::storage::Storage;
#[cfg(feature = "bluetooth")]
use crate::dom::testrunner::TestRunner;
+use crate::dom::trustedtypepolicyfactory::TrustedTypePolicyFactory;
use crate::dom::types::UIEvent;
use crate::dom::webglrenderingcontext::WebGLCommandSender;
#[cfg(feature = "webgpu")]
@@ -247,6 +248,7 @@ pub(crate) struct Window {
session_storage: MutNullableDom<Storage>,
local_storage: MutNullableDom<Storage>,
status: DomRefCell<DOMString>,
+ trusted_types: MutNullableDom<TrustedTypePolicyFactory>,
/// For sending timeline markers. Will be ignored if
/// no devtools server
@@ -1696,6 +1698,11 @@ impl WindowMethods<crate::DomTypeHolder> for Window {
self.as_global_scope()
.structured_clone(cx, value, options, retval)
}
+
+ fn TrustedTypes(&self, can_gc: CanGc) -> DomRoot<TrustedTypePolicyFactory> {
+ self.trusted_types
+ .or_init(|| TrustedTypePolicyFactory::new(self.as_global_scope(), can_gc))
+ }
}
impl Window {
@@ -2922,6 +2929,7 @@ impl Window {
layout_marker: DomRefCell::new(Rc::new(Cell::new(true))),
current_event: DomRefCell::new(None),
theme: Cell::new(PrefersColorScheme::Light),
+ trusted_types: Default::default(),
});
unsafe {
diff --git a/components/script/dom/workerglobalscope.rs b/components/script/dom/workerglobalscope.rs
index 3937f8fbedb..7009f51e29a 100644
--- a/components/script/dom/workerglobalscope.rs
+++ b/components/script/dom/workerglobalscope.rs
@@ -52,6 +52,7 @@ use crate::dom::dedicatedworkerglobalscope::DedicatedWorkerGlobalScope;
use crate::dom::globalscope::GlobalScope;
use crate::dom::performance::Performance;
use crate::dom::promise::Promise;
+use crate::dom::trustedtypepolicyfactory::TrustedTypePolicyFactory;
#[cfg(feature = "webgpu")]
use crate::dom::webgpu::identityhub::IdentityHub;
use crate::dom::window::{base64_atob, base64_btoa};
@@ -122,6 +123,7 @@ pub(crate) struct WorkerGlobalScope {
#[no_trace]
navigation_start: CrossProcessInstant,
performance: MutNullableDom<Performance>,
+ trusted_types: MutNullableDom<TrustedTypePolicyFactory>,
/// A [`TimerScheduler`] used to schedule timers for this [`WorkerGlobalScope`].
/// Timers are handled in the service worker event loop.
@@ -184,6 +186,7 @@ impl WorkerGlobalScope {
performance: Default::default(),
timer_scheduler: RefCell::default(),
insecure_requests_policy,
+ trusted_types: Default::default(),
}
}
@@ -477,6 +480,14 @@ impl WorkerGlobalScopeMethods<crate::DomTypeHolder> for WorkerGlobalScope {
self.upcast::<GlobalScope>()
.structured_clone(cx, value, options, retval)
}
+
+ /// <https://www.w3.org/TR/trusted-types/#dom-windoworworkerglobalscope-trustedtypes>
+ fn TrustedTypes(&self, can_gc: CanGc) -> DomRoot<TrustedTypePolicyFactory> {
+ self.trusted_types.or_init(|| {
+ let global_scope = self.upcast::<GlobalScope>();
+ TrustedTypePolicyFactory::new(global_scope, can_gc)
+ })
+ }
}
impl WorkerGlobalScope {