script_bindings/
realms.rs

1/* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at https://mozilla.org/MPL/2.0/. */
4
5use js::jsapi::{GetCurrentRealmOrNull, JSAutoRealm};
6use js::realm::CurrentRealm;
7
8use crate::DomTypes;
9use crate::interfaces::GlobalScopeHelpers;
10use crate::reflector::DomObject;
11use crate::script_runtime::JSContext;
12
13pub struct AlreadyInRealm(());
14
15impl AlreadyInRealm {
16    #![expect(unsafe_code)]
17    pub fn assert<D: DomTypes>() -> AlreadyInRealm {
18        unsafe {
19            assert!(!GetCurrentRealmOrNull(*D::GlobalScope::get_cx()).is_null());
20        }
21        AlreadyInRealm(())
22    }
23
24    pub fn assert_for_cx(cx: JSContext) -> AlreadyInRealm {
25        unsafe {
26            assert!(!GetCurrentRealmOrNull(*cx).is_null());
27        }
28        AlreadyInRealm(())
29    }
30}
31
32impl<'a, 'b> From<&'a mut CurrentRealm<'b>> for AlreadyInRealm {
33    fn from(_: &'a mut CurrentRealm<'b>) -> AlreadyInRealm {
34        AlreadyInRealm(())
35    }
36}
37
38#[derive(Clone, Copy)]
39pub enum InRealm<'a> {
40    Already(&'a AlreadyInRealm),
41    Entered(&'a JSAutoRealm),
42}
43
44impl<'a> From<&'a AlreadyInRealm> for InRealm<'a> {
45    fn from(token: &'a AlreadyInRealm) -> InRealm<'a> {
46        InRealm::already(token)
47    }
48}
49
50impl<'a> From<&'a JSAutoRealm> for InRealm<'a> {
51    fn from(token: &'a JSAutoRealm) -> InRealm<'a> {
52        InRealm::entered(token)
53    }
54}
55
56impl InRealm<'_> {
57    pub fn already(token: &AlreadyInRealm) -> InRealm<'_> {
58        InRealm::Already(token)
59    }
60
61    pub fn entered(token: &JSAutoRealm) -> InRealm<'_> {
62        InRealm::Entered(token)
63    }
64}
65
66pub fn enter_realm<D: DomTypes>(object: &impl DomObject) -> JSAutoRealm {
67    JSAutoRealm::new(
68        *D::GlobalScope::get_cx(),
69        object.reflector().get_jsobject().get(),
70    )
71}