Skip to content

Commit d368e2e

Browse files
committed
Unified tests of wasm to see if this is the problem found in windows.
1 parent ea3ff88 commit d368e2e

File tree

2 files changed

+142
-167
lines changed

2 files changed

+142
-167
lines changed

source/tests/metacall_wasm_test/CMakeLists.txt

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -127,8 +127,9 @@ add_dependencies(${target}
127127
# Define test
128128
#
129129

130-
if(WIN32 AND OPTION_BUILD_ADDRESS_SANITIZER)
131-
# TODO: This test segfaults in windows when run with addres sanitizer without any output
130+
if(OPTION_BUILD_ADDRESS_SANITIZER)
131+
# TODO: Address sanitizer seems to break with WASM loading,
132+
# we should either review this or instrument properly wasmtime library
132133
return()
133134
endif()
134135

source/tests/metacall_wasm_test/source/metacall_wasm_test.cpp

Lines changed: 139 additions & 165 deletions
Original file line numberDiff line numberDiff line change
@@ -24,73 +24,9 @@
2424

2525
class 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-
9430
void 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

Comments
 (0)