quickjs_oxide/engine/api/core/
context.rs1use super::RuntimeError;
5#[cfg(feature = "test262-host")]
6use super::property::PropertyKey;
7use super::runtime::Runtime;
8use super::value::ObjectRef;
9use super::value::Value;
10
11#[derive(Clone, Debug, PartialEq, Eq)]
13pub struct EvalOptions {
14 pub filename: String,
15 pub transient: bool,
18}
19
20impl EvalOptions {
21 pub fn new(filename: impl Into<String>) -> Self {
22 EvalOptions {
23 filename: filename.into(),
24 transient: false,
25 }
26 }
27
28 #[must_use]
30 pub fn transient(mut self) -> Self {
31 self.transient = true;
32 self
33 }
34}
35
36impl Default for EvalOptions {
37 fn default() -> Self {
38 Self::new(crate::engine::compiler::DEFAULT_EVAL_FILENAME)
39 }
40}
41
42#[derive(Clone, Debug, PartialEq)]
44pub struct FunctionBytecodeRef {
45 function: ObjectRef,
46 #[cfg(test)]
48 pub(crate) stack: StackCode,
49}
50
51#[cfg(test)]
54#[derive(Clone)]
55pub(crate) struct StackCode {
56 pub(crate) root: std::rc::Rc<crate::engine::code::function::UnlinkedFunction>,
57 pub(crate) path: Vec<usize>,
58}
59
60#[cfg(test)]
61impl StackCode {
62 pub(crate) fn function(&self) -> &crate::engine::code::function::UnlinkedFunction {
63 self.path.iter().fold(&self.root, |function, index| {
64 function.constants()[*index]
65 .as_child()
66 .expect("a child-function constant")
67 })
68 }
69}
70
71#[cfg(test)]
72impl std::fmt::Debug for StackCode {
73 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
74 f.debug_struct("StackCode")
75 .field("path", &self.path)
76 .finish()
77 }
78}
79
80#[cfg(test)]
81impl PartialEq for StackCode {
82 fn eq(&self, other: &Self) -> bool {
83 std::rc::Rc::ptr_eq(&self.root, &other.root) && self.path == other.path
84 }
85}
86
87#[derive(Clone, Debug, PartialEq, Eq)]
89pub struct ModuleBytecodeRef {
90 name: String,
91}
92
93impl ModuleBytecodeRef {
94 pub fn name(&self) -> &str {
96 &self.name
97 }
98}
99
100#[derive(Clone, Debug, Default, PartialEq, Eq)]
102pub struct QjsHelpers {
103 pub std: bool,
105 pub script_args: Option<Vec<String>>,
107}
108
109#[derive(Clone)]
111pub struct Context {
112 pub(crate) runtime: Runtime,
113}
114
115impl FunctionBytecodeRef {
116 pub(crate) fn new(
117 function: ObjectRef,
118 #[cfg(test)] source: &[u8],
119 #[cfg(test)] filename: &str,
120 #[cfg(test)] debug_info: crate::engine::code::debug::DebugInfoMode,
121 ) -> Self {
122 FunctionBytecodeRef {
123 function,
124 #[cfg(test)]
125 stack: StackCode {
126 root: std::rc::Rc::new(
127 crate::engine::compiler::compile_unlinked_script_bytes_with_filename(
128 source, filename, debug_info,
129 )
130 .expect("the script compiled once"),
131 ),
132 path: Vec::new(),
133 },
134 }
135 }
136
137 pub(crate) fn function(&self) -> &ObjectRef {
138 &self.function
139 }
140}
141
142impl ModuleBytecodeRef {
143 pub(crate) fn new(name: &str) -> Self {
144 ModuleBytecodeRef {
145 name: name.to_owned(),
146 }
147 }
148}
149
150impl Context {
155 pub fn new(runtime: &Runtime) -> Self {
157 runtime.context()
158 }
159
160 pub fn try_clone(&self) -> Result<Self, RuntimeError> {
161 Ok(self.clone())
162 }
163
164 pub fn runtime(&self) -> &Runtime {
165 &self.runtime
166 }
167
168 pub fn define_module(
174 &self,
175 name: &str,
176 exports: Vec<(String, Value)>,
177 ) -> Result<(), RuntimeError> {
178 let mut entry = self.runtime.enter()?;
179 {
180 let view = entry.view();
181 for (_, value) in &exports {
182 if let Value::Object(ObjectRef { slot })
183 | Value::Symbol(super::value::SymbolRef { slot }) = value
184 {
185 view.own(slot)?;
186 }
187 }
188 }
189 entry.inner.core.forget_module(name);
190 self.runtime.shared.modules.borrow_mut().insert(
191 name.to_owned(),
192 super::runtime::Preloaded::Synthetic(exports),
193 );
194 Ok(())
195 }
196
197 #[cfg(feature = "test262-host")]
199 pub fn install_test262_host(&mut self) -> Result<ObjectRef, RuntimeError> {
200 {
201 let mut entry = self.runtime.enter()?;
202 entry.inner.core.install_test262_host()?;
203 }
204 let global = self.global_object()?;
205 let key = PropertyKey::from_js_string(crate::engine::value::JsString::from_static("$262"));
206 match self.get_property(&global, &key)? {
207 Value::Object(host) => Ok(host),
208 _ => Err(RuntimeError::Invariant("$262 is an object")),
209 }
210 }
211}