tetsy_wasm/builder/
global.rs

1use super::{
2	invoke::{Invoke, Identity},
3	misc::ValueTypeBuilder,
4};
5
6use crate::elements;
7
8/// Global builder
9pub struct GlobalBuilder<F=Identity> {
10	callback: F,
11	value_type: elements::ValueType,
12	is_mutable: bool,
13	init_expr: elements::InitExpr,
14}
15
16impl GlobalBuilder {
17	/// New global builder
18	pub fn new() -> Self {
19		GlobalBuilder::with_callback(Identity)
20	}
21}
22
23impl<F> GlobalBuilder<F> {
24	/// New global builder with callback (in chained context)
25	pub fn with_callback(callback: F) -> Self {
26		GlobalBuilder {
27			callback: callback,
28			value_type: elements::ValueType::I32,
29			init_expr: elements::InitExpr::empty(),
30			is_mutable: false,
31		}
32	}
33
34	/// Set/override resulting global type
35	pub fn with_type(mut self, value_type: elements::ValueType) -> Self {
36		self.value_type = value_type;
37		self
38	}
39
40	/// Set mutabilty to true
41	pub fn mutable(mut self) -> Self {
42		self.is_mutable = true;
43		self
44	}
45
46	/// Set initialization expression instruction for this global (`end` instruction will be added automatically)
47	pub fn init_expr(mut self, instruction: elements::Instruction) -> Self {
48		self.init_expr = elements::InitExpr::new(vec![instruction, elements::Instruction::End]);
49		self
50	}
51
52	/// Start value type builder
53	pub fn value_type(self) -> ValueTypeBuilder<Self> {
54		ValueTypeBuilder::with_callback(self)
55	}
56}
57
58impl<F> GlobalBuilder<F> where F: Invoke<elements::GlobalEntry> {
59	/// Finalize current builder spawning resulting struct
60	pub fn build(self) -> F::Result {
61		self.callback.invoke(
62			elements::GlobalEntry::new(
63				elements::GlobalType::new(self.value_type, self.is_mutable),
64				self.init_expr,
65			)
66		)
67	}
68}
69
70impl<F> Invoke<elements::ValueType> for GlobalBuilder<F> {
71	type Result = Self;
72	fn invoke(self, the_type: elements::ValueType) -> Self {
73		self.with_type(the_type)
74	}
75}
76
77/// New builder for export entry
78pub fn global() -> GlobalBuilder {
79	GlobalBuilder::new()
80}
81
82#[cfg(test)]
83mod tests {
84	use super::global;
85	use crate::elements;
86
87	#[test]
88	fn example() {
89		let entry = global().value_type().i32().build();
90		assert_eq!(entry.global_type().content_type(), elements::ValueType::I32);
91		assert_eq!(entry.global_type().is_mutable(), false);
92	}
93}