2424
2525class metacall_wasm_test : public testing ::Test
2626{
27- protected:
28- void SetUp () override
29- {
30- metacall_initialize ();
31- }
32-
33- void TearDown () override
34- {
35- metacall_destroy ();
36- }
27+ public:
3728};
3829
39- TEST_F (metacall_wasm_test, InitializeAndDestroy)
40- {
41- // This is extremely hacky and causes an error when loading the buffer,
42- // since it is invalid. However, it is currently impossible to initialize a
43- // loader without attempting to load a handle with it. Ideally, there would
44- // be a `metacall_initialize_loader` function or similar.
45- const char dummy_buffer[1 ] = { 0 };
46- metacall_load_from_memory (" wasm" , dummy_buffer, 1 , NULL );
47-
48- ASSERT_EQ ((int )0 , (int )metacall_is_initialized (" wasm" ));
49-
50- // `metacall_destroy` does nothing if Metacall is not initialized, so we
51- // can safely call it here even though we also call it during tear-down.
52- ASSERT_EQ ((int )0 , (int )metacall_destroy ());
53- }
54-
55- /* TODO: Address sanitizer seems to break with WASM loading, we should either review this or instrument properly wasmtime library */
56- #if !defined(__ADDRESS_SANITIZER__)
57- TEST_F (metacall_wasm_test, LoadBinaryFromMemory)
58- {
59- // See https://webassembly.github.io/spec/core/binary/modules.html#binary-module
60- const char empty_module[] = {
61- 0x00 , 0x61 , 0x73 , 0x6d , // Magic bytes
62- 0x01 , 0x00 , 0x00 , 0x00 // Version
63- };
64- ASSERT_EQ ((int )0 , (int )metacall_load_from_memory (" wasm" , empty_module, sizeof (empty_module), NULL ));
65-
66- const char invalid_module[] = { 0 };
67- ASSERT_NE ((int )0 , (int )metacall_load_from_memory (" wasm" , invalid_module, sizeof (invalid_module), NULL ));
68- }
69-
70- TEST_F (metacall_wasm_test, LoadTextFromMemory)
71- {
72- const char *empty_module = " (module)" ;
73- ASSERT_EQ ((int )0 , (int )metacall_load_from_memory (" wasm" , empty_module, strlen (empty_module), NULL ));
74-
75- const char *invalid_module = " (invalid)" ;
76- ASSERT_NE ((int )0 , (int )metacall_load_from_memory (" wasm" , invalid_module, strlen (invalid_module), NULL ));
77- }
78-
79- TEST_F (metacall_wasm_test, LoadFromFile)
80- {
81- const char *empty_module_filename = " empty_module.wat" ;
82- const char *invalid_module_filename = " invalid_module.wat" ;
83-
84- ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , &empty_module_filename, 1 , NULL ));
85- ASSERT_NE ((int )0 , (int )metacall_load_from_file (" wasm" , &invalid_module_filename, 1 , NULL ));
86- }
87-
88- TEST_F (metacall_wasm_test, LoadFromPackage)
89- {
90- ASSERT_EQ ((int )0 , (int )metacall_load_from_package (" wasm" , " empty_module.wasm" , NULL ));
91- ASSERT_NE ((int )0 , (int )metacall_load_from_package (" wasm" , " invalid_module.wasm" , NULL ));
92- }
93-
9430void TestFunction (void *handle, const char *name, const std::vector<enum metacall_value_id> &expected_param_types, enum metacall_value_id expected_return_type)
9531{
9632 void *func = metacall_handle_function (handle, name);
@@ -110,113 +46,151 @@ void TestFunction(void *handle, const char *name, const std::vector<enum metacal
11046 ASSERT_EQ ((enum metacall_value_id)expected_return_type, (enum metacall_value_id)return_type);
11147}
11248
113- TEST_F (metacall_wasm_test, DiscoverFunctions )
49+ TEST_F (metacall_wasm_test, Default )
11450{
115- const char *functions_module_filename = " functions.wat" ;
116- void *handle = NULL ;
51+ ASSERT_EQ ((int )0 , (int )metacall_initialize ());
11752
118- ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , &functions_module_filename, 1 , &handle));
53+ /* LoadBinaryFromMemory */
54+ {
55+ /* See https://webassembly.github.io/spec/core/binary/modules.html#binary-module */
56+ const char empty_module[] = {
57+ 0x00 , 0x61 , 0x73 , 0x6d , // Magic bytes
58+ 0x01 , 0x00 , 0x00 , 0x00 // Version
59+ };
60+ ASSERT_EQ ((int )0 , (int )metacall_load_from_memory (" wasm" , empty_module, sizeof (empty_module), NULL ));
61+
62+ const char invalid_module[] = { 0 };
63+ ASSERT_NE ((int )0 , (int )metacall_load_from_memory (" wasm" , invalid_module, sizeof (invalid_module), NULL ));
64+ }
11965
120- ASSERT_EQ ((void *)NULL , (void *)metacall_handle_function (handle, " does_not_exist" ));
66+ /* LoadTextFromMemory */
67+ {
68+ const char *empty_module = " (module)" ;
69+ ASSERT_EQ ((int )0 , (int )metacall_load_from_memory (" wasm" , empty_module, strlen (empty_module), NULL ));
12170
122- TestFunction (handle, " none_ret_none" , {}, METACALL_INVALID);
123- TestFunction (handle, " i64_ret_none" , { METACALL_LONG }, METACALL_INVALID);
124- TestFunction (handle, " i32_f32_i64_f64_ret_none" , { METACALL_INT, METACALL_FLOAT, METACALL_LONG, METACALL_DOUBLE }, METACALL_INVALID);
125- TestFunction (handle, " none_ret_i32" , {}, METACALL_INT);
71+ const char *invalid_module = " (invalid)" ;
72+ ASSERT_NE ((int )0 , (int )metacall_load_from_memory (" wasm" , invalid_module, strlen (invalid_module), NULL ));
73+ }
12674
127- TestFunction (handle, " none_ret_i32_f32_i64_f64" , {}, METACALL_ARRAY);
128- TestFunction (handle, " i32_f32_i64_f64_ret_i32_f32_i64_f64" , { METACALL_INT, METACALL_FLOAT, METACALL_LONG, METACALL_DOUBLE }, METACALL_ARRAY);
129- }
75+ /* LoadFromFile */
76+ {
77+ const char *empty_module_filename = " empty_module.wat" ;
78+ const char *invalid_module_filename = " invalid_module.wat" ;
13079
131- TEST_F (metacall_wasm_test, CallFunctions)
132- {
133- const char *functions_module_filename = " functions.wat" ;
134-
135- ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , &functions_module_filename, 1 , NULL ));
136-
137- void *ret = metacall (" none_ret_none" );
138- ASSERT_NE ((void *)NULL , (void *)ret);
139- ASSERT_EQ ((enum metacall_value_id)METACALL_NULL, (enum metacall_value_id)metacall_value_id (ret));
140- metacall_value_destroy (ret);
141-
142- ret = metacall (" i64_ret_none" , 0L );
143- ASSERT_NE ((void *)NULL , (void *)ret);
144- ASSERT_EQ ((enum metacall_value_id)METACALL_NULL, (enum metacall_value_id)metacall_value_id (ret));
145- metacall_value_destroy (ret);
146-
147- ret = metacall (" i32_f32_i64_f64_ret_none" , 0 , 0 .0f , 0L , 0.0 );
148- ASSERT_NE ((void *)NULL , (void *)ret);
149- ASSERT_EQ ((enum metacall_value_id)METACALL_NULL, (enum metacall_value_id)metacall_value_id (ret));
150- metacall_value_destroy (ret);
151-
152- ret = metacall (" none_ret_i32" );
153- ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (ret));
154- ASSERT_EQ ((int )1 , (int )metacall_value_to_int (ret));
155- metacall_value_destroy (ret);
156-
157- ret = metacall (" none_ret_i32_f32_i64_f64" );
158- ASSERT_EQ ((enum metacall_value_id)METACALL_ARRAY, (enum metacall_value_id)metacall_value_id (ret));
159-
160- void **values = metacall_value_to_array (ret);
161- ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (values[0 ]));
162- ASSERT_EQ ((enum metacall_value_id)METACALL_FLOAT, (enum metacall_value_id)metacall_value_id (values[1 ]));
163- ASSERT_EQ ((enum metacall_value_id)METACALL_LONG, (enum metacall_value_id)metacall_value_id (values[2 ]));
164- ASSERT_EQ ((enum metacall_value_id)METACALL_DOUBLE, (enum metacall_value_id)metacall_value_id (values[3 ]));
165- ASSERT_EQ ((int )1 , (int )metacall_value_to_int (values[0 ]));
166- ASSERT_EQ ((float )2 .0f , (float )metacall_value_to_float (values[1 ]));
167- ASSERT_EQ ((long )3 , (long )metacall_value_to_long (values[2 ]));
168- ASSERT_EQ ((double )4.0 , (double )metacall_value_to_double (values[3 ]));
169- metacall_value_destroy (ret);
170-
171- ret = metacall (" i32_f32_i64_f64_ret_i32_f32_i64_f64" , 0 , 0 , 0 , 0 );
172- ASSERT_EQ ((enum metacall_value_id)METACALL_ARRAY, (enum metacall_value_id)metacall_value_id (ret));
173-
174- values = metacall_value_to_array (ret);
175- ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (values[0 ]));
176- ASSERT_EQ ((enum metacall_value_id)METACALL_FLOAT, (enum metacall_value_id)metacall_value_id (values[1 ]));
177- ASSERT_EQ ((enum metacall_value_id)METACALL_LONG, (enum metacall_value_id)metacall_value_id (values[2 ]));
178- ASSERT_EQ ((enum metacall_value_id)METACALL_DOUBLE, (enum metacall_value_id)metacall_value_id (values[3 ]));
179- ASSERT_EQ ((int )1 , (int )metacall_value_to_int (values[0 ]));
180- ASSERT_EQ ((float )2 .0f , (float )metacall_value_to_float (values[1 ]));
181- ASSERT_EQ ((long )3 , (long )metacall_value_to_long (values[2 ]));
182- ASSERT_EQ ((double )4.0 , (double )metacall_value_to_double (values[3 ]));
183- metacall_value_destroy (ret);
184-
185- // It should exit with illegal instruction
186- #if defined(unix) || defined(__unix__) || defined(__unix) || \
187- defined (linux) || defined (__linux__) || defined (__linux) || defined (__gnu_linux)
188- ASSERT_EXIT ((metacall (" trap" ), exit (0 )), ::testing::KilledBySignal (SIGILL), " .*" );
189- #endif
190- }
80+ ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , &empty_module_filename, 1 , NULL ));
81+ ASSERT_NE ((int )0 , (int )metacall_load_from_file (" wasm" , &invalid_module_filename, 1 , NULL ));
82+ }
19183
192- TEST_F (metacall_wasm_test, LinkModules)
193- {
194- const char *modules[] = {
195- " exports1.wat" ,
196- " exports2.wat" ,
197- " imports.wat"
198- };
199-
200- ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , modules, sizeof (modules) / sizeof (modules[0 ]), NULL ));
201-
202- void *ret = metacall (" duplicate_func_i32" );
203- ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (ret));
204- ASSERT_EQ ((int )1 , (int )metacall_value_to_int (ret));
205- metacall_value_destroy (ret);
206-
207- ret = metacall (" duplicate_func_i64" );
208- ASSERT_EQ ((enum metacall_value_id)METACALL_LONG, (enum metacall_value_id)metacall_value_id (ret));
209- ASSERT_EQ ((long )2 , (long )metacall_value_to_long (ret));
210- metacall_value_destroy (ret);
211- }
84+ /* LoadFromPackage */
85+ {
86+ ASSERT_EQ ((int )0 , (int )metacall_load_from_package (" wasm" , " empty_module.wasm" , NULL ));
87+ ASSERT_NE ((int )0 , (int )metacall_load_from_package (" wasm" , " invalid_module.wasm" , NULL ));
88+ }
21289
213- TEST_F (metacall_wasm_test, InvalidLinkModules)
214- {
215- const char *modules[] = {
216- " exports1.wat" ,
217- " imports.wat"
218- };
90+ /* DiscoverFunctions & CallFunctions */
91+ {
92+ const char *functions_module_filename = " functions.wat" ;
93+ void *handle = NULL ;
94+
95+ ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , &functions_module_filename, 1 , &handle));
96+
97+ ASSERT_EQ ((void *)NULL , (void *)metacall_handle_function (handle, " does_not_exist" ));
98+
99+ TestFunction (handle, " none_ret_none" , {}, METACALL_INVALID);
100+ TestFunction (handle, " i64_ret_none" , { METACALL_LONG }, METACALL_INVALID);
101+ TestFunction (handle, " i32_f32_i64_f64_ret_none" , { METACALL_INT, METACALL_FLOAT, METACALL_LONG, METACALL_DOUBLE }, METACALL_INVALID);
102+ TestFunction (handle, " none_ret_i32" , {}, METACALL_INT);
103+ TestFunction (handle, " none_ret_i32_f32_i64_f64" , {}, METACALL_ARRAY);
104+ TestFunction (handle, " i32_f32_i64_f64_ret_i32_f32_i64_f64" , { METACALL_INT, METACALL_FLOAT, METACALL_LONG, METACALL_DOUBLE }, METACALL_ARRAY);
105+
106+ void *ret = metacallht_s (handle, " none_ret_none" , {}, 0 );
107+ ASSERT_NE ((void *)NULL , (void *)ret);
108+ ASSERT_EQ ((enum metacall_value_id)METACALL_NULL, (enum metacall_value_id)metacall_value_id (ret));
109+ metacall_value_destroy (ret);
110+
111+ const enum metacall_value_id i64_ret_none_ids[] = { METACALL_LONG };
112+ ret = metacallht_s (handle, " i64_ret_none" , i64_ret_none_ids, 1 , 0L );
113+ ASSERT_NE ((void *)NULL , (void *)ret);
114+ ASSERT_EQ ((enum metacall_value_id)METACALL_NULL, (enum metacall_value_id)metacall_value_id (ret));
115+ metacall_value_destroy (ret);
116+
117+ const enum metacall_value_id i32_f32_i64_f64_ret_none_ids[] = { METACALL_INT, METACALL_FLOAT, METACALL_LONG, METACALL_DOUBLE };
118+ ret = metacallht_s (handle, " i32_f32_i64_f64_ret_none" , i32_f32_i64_f64_ret_none_ids, 4 , 0 , 0 .0f , 0L , 0.0 );
119+ ASSERT_NE ((void *)NULL , (void *)ret);
120+ ASSERT_EQ ((enum metacall_value_id)METACALL_NULL, (enum metacall_value_id)metacall_value_id (ret));
121+ metacall_value_destroy (ret);
122+
123+ ret = metacallht_s (handle, " none_ret_i32" , {}, 0 );
124+ ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (ret));
125+ ASSERT_EQ ((int )1 , (int )metacall_value_to_int (ret));
126+ metacall_value_destroy (ret);
127+
128+ ret = metacallht_s (handle, " none_ret_i32_f32_i64_f64" , {}, 0 );
129+ ASSERT_EQ ((enum metacall_value_id)METACALL_ARRAY, (enum metacall_value_id)metacall_value_id (ret));
130+
131+ void **values = metacall_value_to_array (ret);
132+ ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (values[0 ]));
133+ ASSERT_EQ ((enum metacall_value_id)METACALL_FLOAT, (enum metacall_value_id)metacall_value_id (values[1 ]));
134+ ASSERT_EQ ((enum metacall_value_id)METACALL_LONG, (enum metacall_value_id)metacall_value_id (values[2 ]));
135+ ASSERT_EQ ((enum metacall_value_id)METACALL_DOUBLE, (enum metacall_value_id)metacall_value_id (values[3 ]));
136+ ASSERT_EQ ((int )1 , (int )metacall_value_to_int (values[0 ]));
137+ ASSERT_EQ ((float )2 .0f , (float )metacall_value_to_float (values[1 ]));
138+ ASSERT_EQ ((long )3 , (long )metacall_value_to_long (values[2 ]));
139+ ASSERT_EQ ((double )4.0 , (double )metacall_value_to_double (values[3 ]));
140+ metacall_value_destroy (ret);
141+
142+ const enum metacall_value_id i32_f32_i64_f64_ret_i32_f32_i64_f64_ids[] = { METACALL_INT, METACALL_FLOAT, METACALL_LONG, METACALL_DOUBLE };
143+ ret = metacallht_s (handle, " i32_f32_i64_f64_ret_i32_f32_i64_f64" , i32_f32_i64_f64_ret_i32_f32_i64_f64_ids, 4 , 0 , 0 , 0 , 0 );
144+ ASSERT_EQ ((enum metacall_value_id)METACALL_ARRAY, (enum metacall_value_id)metacall_value_id (ret));
145+
146+ values = metacall_value_to_array (ret);
147+ ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (values[0 ]));
148+ ASSERT_EQ ((enum metacall_value_id)METACALL_FLOAT, (enum metacall_value_id)metacall_value_id (values[1 ]));
149+ ASSERT_EQ ((enum metacall_value_id)METACALL_LONG, (enum metacall_value_id)metacall_value_id (values[2 ]));
150+ ASSERT_EQ ((enum metacall_value_id)METACALL_DOUBLE, (enum metacall_value_id)metacall_value_id (values[3 ]));
151+ ASSERT_EQ ((int )1 , (int )metacall_value_to_int (values[0 ]));
152+ ASSERT_EQ ((float )2 .0f , (float )metacall_value_to_float (values[1 ]));
153+ ASSERT_EQ ((long )3 , (long )metacall_value_to_long (values[2 ]));
154+ ASSERT_EQ ((double )4.0 , (double )metacall_value_to_double (values[3 ]));
155+ metacall_value_destroy (ret);
156+
157+ // It should exit with illegal instruction
158+ #if defined(unix) || defined(__unix__) || defined(__unix) || \
159+ defined (linux) || defined (__linux__) || defined (__linux) || defined (__gnu_linux)
160+ ASSERT_EXIT ((metacallht_s (handle, " trap" , {}, 0 ), exit (0 )), ::testing::ExitedWithCode (0 ), " .*" );
161+ #endif
162+ }
163+
164+ /* LinkModules */
165+ {
166+ const char *modules[] = {
167+ " exports1.wat" ,
168+ " exports2.wat" ,
169+ " imports.wat"
170+ };
171+
172+ ASSERT_EQ ((int )0 , (int )metacall_load_from_file (" wasm" , modules, sizeof (modules) / sizeof (modules[0 ]), NULL ));
173+
174+ void *ret = metacall (" duplicate_func_i32" );
175+ ASSERT_EQ ((enum metacall_value_id)METACALL_INT, (enum metacall_value_id)metacall_value_id (ret));
176+ ASSERT_EQ ((int )1 , (int )metacall_value_to_int (ret));
177+ metacall_value_destroy (ret);
178+
179+ ret = metacall (" duplicate_func_i64" );
180+ ASSERT_EQ ((enum metacall_value_id)METACALL_LONG, (enum metacall_value_id)metacall_value_id (ret));
181+ ASSERT_EQ ((long )2 , (long )metacall_value_to_long (ret));
182+ metacall_value_destroy (ret);
183+ }
219184
220- ASSERT_EQ ((int )1 , (int )metacall_load_from_file (" wasm" , modules, sizeof (modules) / sizeof (modules[0 ]), NULL ));
185+ /* InvalidLinkModules */
186+ {
187+ const char *modules[] = {
188+ " exports1.wat" ,
189+ " imports.wat"
190+ };
191+
192+ ASSERT_EQ ((int )1 , (int )metacall_load_from_file (" wasm" , modules, sizeof (modules) / sizeof (modules[0 ]), NULL ));
193+ }
194+
195+ ASSERT_EQ ((int )0 , (int )metacall_destroy ());
221196}
222- #endif
0 commit comments