Skip to content

Commit df495db

Browse files
committed
[wasmtime] extract running module into function
Signed-off-by: Maximilian Hüter <[email protected]>
1 parent 6f0a3c5 commit df495db

File tree

1 file changed

+106
-40
lines changed

1 file changed

+106
-40
lines changed

src/libcrun/handlers/wasmtime.c

Lines changed: 106 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
#include <assert.h>
3333
#include <stdio.h>
3434
#include <stdlib.h>
35+
#include <string.h>
3536

3637
#ifdef HAVE_DLOPEN
3738
# include <dlfcn.h>
@@ -44,16 +45,110 @@
4445
#endif
4546

4647
#if HAVE_DLOPEN && HAVE_WASMTIME
48+
static void
49+
libwasmtime_run_module (void *cookie, char *const argv[], wasm_engine_t *engine, wasm_byte_vec_t *wasm);
50+
51+
static void
52+
libwasmtime_run_component (void *cookie, char *const argv[], wasm_engine_t *engine, wasm_byte_vec_t *wasm);
53+
4754
static int
4855
libwasmtime_exec (void *cookie, libcrun_container_t *container arg_unused,
4956
const char *pathname, char *const argv[])
5057
{
51-
size_t args_size = 0;
52-
char *const *arg;
5358
wasm_byte_vec_t error_message;
5459
wasm_byte_vec_t wasm_bytes;
5560
wasm_engine_t *(*wasm_engine_new) ();
5661
wasmtime_error_t *(*wasmtime_wat2wasm) (const char *wat, size_t wat_len, wasm_byte_vec_t *out);
62+
void (*wasm_byte_vec_new_uninitialized) (wasm_byte_vec_t *, size_t);
63+
wasmtime_error_t *(*wasmtime_module_validate) (wasm_engine_t *engine, const uint8_t *wasm, size_t wasm_len);
64+
void (*wasmtime_error_message) (const wasmtime_error_t *error, wasm_name_t *message);
65+
void (*wasmtime_error_delete) (wasmtime_error_t *error);
66+
67+
wasmtime_wat2wasm = dlsym (cookie, "wasmtime_wat2wasm");
68+
wasm_engine_new = dlsym (cookie, "wasm_engine_new");
69+
wasm_byte_vec_new_uninitialized = dlsym (cookie, "wasm_byte_vec_new_uninitialized");
70+
wasmtime_module_validate = dlsym (cookie, "wasmtime_module_validate");
71+
wasmtime_error_delete = dlsym (cookie, "wasmtime_error_delete");
72+
wasmtime_error_message = dlsym (cookie, "wasmtime_error_message");
73+
74+
if (wasmtime_wat2wasm == NULL
75+
|| wasm_engine_new == NULL
76+
|| wasm_byte_vec_new_uninitialized == NULL
77+
|| wasmtime_module_validate == NULL
78+
|| wasmtime_error_delete == NULL
79+
|| wasmtime_error_message == NULL)
80+
error (EXIT_FAILURE, 0, "could not find symbol in `libwasmtime.so`");
81+
82+
// Set up wasmtime context
83+
wasm_engine_t *engine = wasm_engine_new ();
84+
assert (engine != NULL);
85+
86+
wasm_byte_vec_t wasm;
87+
// Load and parse container entrypoint
88+
FILE *file = fopen (pathname, "rbe");
89+
if (! file)
90+
error (EXIT_FAILURE, 0, "error loading entrypoint");
91+
fseek (file, 0L, SEEK_END);
92+
size_t file_size = ftell (file);
93+
wasm_byte_vec_new_uninitialized (&wasm, file_size);
94+
fseek (file, 0L, SEEK_SET);
95+
if (fread (wasm.data, file_size, 1, file) != 1)
96+
error (EXIT_FAILURE, 0, "error load");
97+
fclose (file);
98+
99+
// If entrypoint contains a webassembly text format
100+
// compile it on the fly and convert to equivalent
101+
// binary format.
102+
if (has_suffix (pathname, "wat") > 0)
103+
{
104+
wasmtime_error_t *err = wasmtime_wat2wasm ((char *) &wasm_bytes, file_size, &wasm);
105+
if (err != NULL)
106+
{
107+
wasmtime_error_message (err, &error_message);
108+
wasmtime_error_delete (err);
109+
error (EXIT_FAILURE, 0, "failed while compiling wat to wasm binary : %.*s", (int) error_message.size, error_message.data);
110+
}
111+
wasm = wasm_bytes;
112+
}
113+
114+
// Check if it is a valid webassembly module or
115+
// a component.
116+
bool is_wasm_module = true;
117+
wasmtime_error_t *err = wasmtime_module_validate (engine, (uint8_t *) wasm.data, wasm.size);
118+
if (err != NULL)
119+
{
120+
wasmtime_error_message (err, &error_message);
121+
wasmtime_error_delete (err);
122+
123+
if (strcmp ((char *) error_message.data, "component passed to module validation") != 0)
124+
{
125+
error (EXIT_FAILURE, 0, "failed to validate module: %.*s", (int) error_message.size, error_message.data);
126+
}
127+
128+
err = NULL;
129+
is_wasm_module = false;
130+
}
131+
132+
if (is_wasm_module)
133+
{
134+
libwasmtime_run_module (cookie, argv, engine, &wasm);
135+
}
136+
else
137+
{
138+
libwasmtime_run_component (cookie, argv, engine, &wasm);
139+
}
140+
141+
exit (EXIT_SUCCESS);
142+
}
143+
144+
static void
145+
libwasmtime_run_module (void *cookie, char *const argv[], wasm_engine_t *engine, wasm_byte_vec_t *wasm)
146+
{
147+
size_t args_size = 0;
148+
char *const *arg;
149+
wasm_byte_vec_t error_message;
150+
151+
// Load needed functions
57152
void (*wasm_engine_delete) (wasm_engine_t *);
58153
void (*wasm_byte_vec_delete) (wasm_byte_vec_t *);
59154
void (*wasm_byte_vec_new_uninitialized) (wasm_byte_vec_t *, size_t);
@@ -100,8 +195,6 @@ libwasmtime_exec (void *cookie, libcrun_container_t *container arg_unused,
100195
void (*wasmtime_error_delete) (wasmtime_error_t *error);
101196
bool (*wasi_config_preopen_dir) (wasi_config_t *config, const char *path, const char *guest_path);
102197

103-
wasmtime_wat2wasm = dlsym (cookie, "wasmtime_wat2wasm");
104-
wasm_engine_new = dlsym (cookie, "wasm_engine_new");
105198
wasm_engine_delete = dlsym (cookie, "wasm_engine_delete");
106199
wasm_byte_vec_delete = dlsym (cookie, "wasm_byte_vec_delete");
107200
wasm_byte_vec_new_uninitialized = dlsym (cookie, "wasm_byte_vec_new_uninitialized");
@@ -127,21 +220,18 @@ libwasmtime_exec (void *cookie, libcrun_container_t *container arg_unused,
127220
wasmtime_error_message = dlsym (cookie, "wasmtime_error_message");
128221
wasi_config_preopen_dir = dlsym (cookie, "wasi_config_preopen_dir");
129222

130-
if (wasm_engine_new == NULL || wasm_engine_delete == NULL || wasm_byte_vec_delete == NULL
223+
if (wasm_engine_delete == NULL || wasm_byte_vec_delete == NULL
131224
|| wasm_byte_vec_new_uninitialized == NULL || wasi_config_new == NULL || wasmtime_store_new == NULL
132225
|| wasmtime_store_context == NULL || wasmtime_linker_new == NULL || wasmtime_linker_define_wasi == NULL
133226
|| wasmtime_module_new == NULL || wasi_config_inherit_argv == NULL || wasi_config_inherit_stdout == NULL
134227
|| wasi_config_inherit_stdin == NULL || wasi_config_inherit_stderr == NULL
135228
|| wasi_config_inherit_env == NULL || wasmtime_context_set_wasi == NULL
136229
|| wasmtime_linker_module == NULL || wasmtime_linker_get_default == NULL || wasmtime_func_call == NULL
137230
|| wasmtime_module_delete == NULL || wasmtime_store_delete == NULL || wasi_config_set_argv == NULL
138-
|| wasmtime_error_delete == NULL || wasmtime_error_message == NULL || wasi_config_preopen_dir == NULL
139-
|| wasmtime_wat2wasm == NULL)
231+
|| wasmtime_error_delete == NULL || wasmtime_error_message == NULL || wasi_config_preopen_dir == NULL)
140232
error (EXIT_FAILURE, 0, "could not find symbol in `libwasmtime.so`");
141233

142234
// Set up wasmtime context
143-
wasm_engine_t *engine = wasm_engine_new ();
144-
assert (engine != NULL);
145235
wasmtime_store_t *store = wasmtime_store_new (engine, NULL, NULL);
146236
assert (store != NULL);
147237
wasmtime_context_t *context = wasmtime_store_context (store);
@@ -156,44 +246,16 @@ libwasmtime_exec (void *cookie, libcrun_container_t *container arg_unused,
156246
error (EXIT_FAILURE, 0, "failed to link wasi: %.*s", (int) error_message.size, error_message.data);
157247
}
158248

159-
wasm_byte_vec_t wasm;
160-
// Load and parse container entrypoint
161-
FILE *file = fopen (pathname, "rbe");
162-
if (! file)
163-
error (EXIT_FAILURE, 0, "error loading entrypoint");
164-
fseek (file, 0L, SEEK_END);
165-
size_t file_size = ftell (file);
166-
wasm_byte_vec_new_uninitialized (&wasm, file_size);
167-
fseek (file, 0L, SEEK_SET);
168-
if (fread (wasm.data, file_size, 1, file) != 1)
169-
error (EXIT_FAILURE, 0, "error load");
170-
fclose (file);
171-
172-
// If entrypoint contains a webassembly text format
173-
// compile it on the fly and convert to equivalent
174-
// binary format.
175-
if (has_suffix (pathname, "wat") > 0)
176-
{
177-
wasmtime_error_t *err = wasmtime_wat2wasm ((char *) &wasm_bytes, file_size, &wasm);
178-
if (err != NULL)
179-
{
180-
wasmtime_error_message (err, &error_message);
181-
wasmtime_error_delete (err);
182-
error (EXIT_FAILURE, 0, "failed while compiling wat to wasm binary : %.*s", (int) error_message.size, error_message.data);
183-
}
184-
wasm = wasm_bytes;
185-
}
186-
187249
// Compile wasm modules
188250
wasmtime_module_t *module = NULL;
189-
err = wasmtime_module_new (engine, (uint8_t *) wasm.data, wasm.size, &module);
251+
err = wasmtime_module_new (engine, (uint8_t *) wasm->data, wasm->size, &module);
190252
if (! module)
191253
{
192254
wasmtime_error_message (err, &error_message);
193255
wasmtime_error_delete (err);
194256
error (EXIT_FAILURE, 0, "failed to compile module: %.*s", (int) error_message.size, error_message.data);
195257
}
196-
wasm_byte_vec_delete (&wasm);
258+
wasm_byte_vec_delete (wasm);
197259

198260
// Init WASI program
199261
wasi_config_t *wasi_config = wasi_config_new ("crun_wasi_program");
@@ -249,8 +311,12 @@ libwasmtime_exec (void *cookie, libcrun_container_t *container arg_unused,
249311
wasmtime_module_delete (module);
250312
wasmtime_store_delete (store);
251313
wasm_engine_delete (engine);
314+
}
252315

253-
exit (EXIT_SUCCESS);
316+
static void
317+
libwasmtime_run_component (void *cookie, char *const argv[], wasm_engine_t *engine, wasm_byte_vec_t *wasm)
318+
{
319+
error (EXIT_FAILURE, 0, "running components is not yet implemented!");
254320
}
255321

256322
static int

0 commit comments

Comments
 (0)