@@ -14,16 +14,16 @@ fn reverse_string(a: String) -> String {
14
14
}
15
15
16
16
#[ rustler:: nif]
17
- fn wasm_example ( source : String , f : String ) -> Result < i32 , Error > {
17
+ fn wasm_example_0 ( source : String , f : String ) -> Result < i32 , Error > {
18
18
// return Ok(5);
19
19
//return Err(Error::Term(Box::new("hello")));
20
- return match wasm_example_interal ( source, f) {
20
+ return match wasm_example_0_internal ( source, f) {
21
21
Ok ( v) => Ok ( v) ,
22
22
Err ( e) => Err ( Error :: Term ( Box :: new ( e. to_string ( ) ) ) )
23
23
}
24
24
}
25
25
26
- fn wasm_example_interal ( source : String , f : String ) -> Result < i32 , anyhow:: Error > {
26
+ fn wasm_example_0_internal ( source : String , f : String ) -> Result < i32 , anyhow:: Error > {
27
27
let engine = Engine :: default ( ) ;
28
28
29
29
// We start off by creating a `Module` which represents a compiled form
@@ -60,4 +60,100 @@ fn wasm_example_interal(source: String, f: String) -> Result<i32, anyhow::Error>
60
60
return Ok ( result) ;
61
61
}
62
62
63
- rustler:: init!( "Elixir.ComponentsGuide.Rustler.Math" , [ add, reverse_string, wasm_example] ) ;
63
+ #[ rustler:: nif]
64
+ fn wasm_example_1_i32 ( source : String , f : String , a : i32 ) -> Result < i32 , Error > {
65
+ return match wasm_example_1_i32_internal ( source, f, a) {
66
+ Ok ( v) => Ok ( v) ,
67
+ Err ( e) => Err ( Error :: Term ( Box :: new ( e. to_string ( ) ) ) )
68
+ }
69
+ }
70
+
71
+ fn wasm_example_1_i32_internal ( source : String , f : String , a : i32 ) -> Result < i32 , anyhow:: Error > {
72
+ let engine = Engine :: default ( ) ;
73
+
74
+ // We start off by creating a `Module` which represents a compiled form
75
+ // of our input wasm module. In this case it'll be JIT-compiled after
76
+ // we parse the text format.
77
+ let module = Module :: new ( & engine, source) ?;
78
+
79
+ // A `Store` is what will own instances, functions, globals, etc. All wasm
80
+ // items are stored within a `Store`, and it's what we'll always be using to
81
+ // interact with the wasm world. Custom data can be stored in stores but for
82
+ // now we just use `()`.
83
+ let mut store = Store :: new ( & engine, ( ) ) ;
84
+
85
+ // With a compiled `Module` we can then instantiate it, creating
86
+ // an `Instance` which we can actually poke at functions on.
87
+ let instance = Instance :: new ( & mut store, & module, & [ ] ) ?;
88
+
89
+ // The `Instance` gives us access to various exported functions and items,
90
+ // which we access here to pull out our `answer` exported function and
91
+ // run it.
92
+ let answer = instance
93
+ . get_func ( & mut store, & f)
94
+ . expect ( & format ! ( "{} was not an exported function" , f) ) ;
95
+
96
+ // There's a few ways we can call the `answer` `Func` value. The easiest
97
+ // is to statically assert its signature with `typed` (in this case
98
+ // asserting it takes no arguments and returns one i32) and then call it.
99
+ let answer = answer. typed :: < ( i32 ) , i32 , _ > ( & store) ?;
100
+
101
+ // And finally we can call our function! Note that the error propagation
102
+ // with `?` is done to handle the case where the wasm function traps.
103
+ let result = answer. call ( & mut store, ( a) ) ?;
104
+
105
+ return Ok ( result) ;
106
+ }
107
+
108
+ #[ rustler:: nif]
109
+ fn wasm_example_2_i32 ( source : String , f : String , a : i32 , b : i32 ) -> Result < i32 , Error > {
110
+ return match wasm_example_2_i32_internal ( source, f, a, b) {
111
+ Ok ( v) => Ok ( v) ,
112
+ Err ( e) => Err ( Error :: Term ( Box :: new ( e. to_string ( ) ) ) )
113
+ }
114
+ }
115
+
116
+ fn wasm_example_2_i32_internal ( source : String , f : String , a : i32 , b : i32 ) -> Result < i32 , anyhow:: Error > {
117
+ let engine = Engine :: default ( ) ;
118
+
119
+ // We start off by creating a `Module` which represents a compiled form
120
+ // of our input wasm module. In this case it'll be JIT-compiled after
121
+ // we parse the text format.
122
+ let module = Module :: new ( & engine, source) ?;
123
+
124
+ // A `Store` is what will own instances, functions, globals, etc. All wasm
125
+ // items are stored within a `Store`, and it's what we'll always be using to
126
+ // interact with the wasm world. Custom data can be stored in stores but for
127
+ // now we just use `()`.
128
+ let mut store = Store :: new ( & engine, ( ) ) ;
129
+
130
+ // With a compiled `Module` we can then instantiate it, creating
131
+ // an `Instance` which we can actually poke at functions on.
132
+ let instance = Instance :: new ( & mut store, & module, & [ ] ) ?;
133
+
134
+ // The `Instance` gives us access to various exported functions and items,
135
+ // which we access here to pull out our `answer` exported function and
136
+ // run it.
137
+ let answer = instance
138
+ . get_func ( & mut store, & f)
139
+ . expect ( & format ! ( "{} was not an exported function" , f) ) ;
140
+
141
+ // There's a few ways we can call the `answer` `Func` value. The easiest
142
+ // is to statically assert its signature with `typed` (in this case
143
+ // asserting it takes no arguments and returns one i32) and then call it.
144
+ let answer = answer. typed :: < ( i32 , i32 ) , i32 , _ > ( & store) ?;
145
+
146
+ // And finally we can call our function! Note that the error propagation
147
+ // with `?` is done to handle the case where the wasm function traps.
148
+ let result = answer. call ( & mut store, ( a, b) ) ?;
149
+
150
+ return Ok ( result) ;
151
+ }
152
+
153
+ rustler:: init!( "Elixir.ComponentsGuide.Rustler.Math" , [
154
+ add,
155
+ reverse_string,
156
+ wasm_example_0,
157
+ wasm_example_1_i32,
158
+ wasm_example_2_i32
159
+ ] ) ;
0 commit comments