summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYuta Saito <kateinoigakukun@gmail.com>2023-05-14 03:59:39 +0000
committerYuta Saito <kateinoigakukun@gmail.com>2023-05-14 14:17:30 +0900
commitedca57e6e37032cb4583f8d731eb81db94e3992d (patch)
tree5b845c77fe014b190d47a035b1afa4e4cfd51e29
parentb632566f7efa758ece6963dcc8b4f3674a39b8d1 (diff)
downloadruby-edca57e6e37032cb4583f8d731eb81db94e3992d.tar.gz
[wasm] Fix `unreachable` error during printing setjmp trace message
-rw-r--r--wasm/setjmp.c37
1 files changed, 26 insertions, 11 deletions
diff --git a/wasm/setjmp.c b/wasm/setjmp.c
index 1e69cb1c64..90420877a8 100644
--- a/wasm/setjmp.c
+++ b/wasm/setjmp.c
@@ -29,10 +29,25 @@
#include "wasm/setjmp.h"
#ifdef RB_WASM_ENABLE_DEBUG_LOG
-# include <stdio.h>
-# define RB_WASM_DEBUG_LOG(...) fprintf(stderr, __VA_ARGS__)
+# include <wasi/api.h>
+# include <unistd.h>
+// NOTE: We can't use printf() and most of library function that are
+// Asyncified due to the use of them in the application itself.
+// Use of printf() causes "unreachable" error because Asyncified
+// function misunderstands Asyncify's internal state during
+// start_unwind()...stop_unwind() and start_rewind()...stop_rewind().
+# define RB_WASM_DEBUG_LOG_INTERNAL(msg) do { \
+ const uint8_t *msg_start = (uint8_t *)msg; \
+ const uint8_t *msg_end = msg_start; \
+ for (; *msg_end != '\0'; msg_end++) {} \
+ __wasi_ciovec_t iov = {.buf = msg_start, .buf_len = msg_end - msg_start}; \
+ size_t nwritten; \
+ __wasi_fd_write(STDERR_FILENO, &iov, 1, &nwritten); \
+} while (0)
+# define RB_WASM_DEBUG_LOG(msg) \
+ RB_WASM_DEBUG_LOG_INTERNAL(__FILE__ ":" STRINGIZE(__LINE__) ": " msg "\n")
#else
-# define RB_WASM_DEBUG_LOG(...)
+# define RB_WASM_DEBUG_LOG(msg)
#endif
enum rb_wasm_jmp_buf_state {
@@ -63,10 +78,10 @@ __attribute__((noinline))
int
_rb_wasm_setjmp_internal(rb_wasm_jmp_buf *env)
{
- RB_WASM_DEBUG_LOG("[%s] env = %p, env->state = %d, _rb_wasm_active_jmpbuf = %p\n", __func__, env, env->state, _rb_wasm_active_jmpbuf);
+ RB_WASM_DEBUG_LOG("enter _rb_wasm_setjmp_internal");
switch (env->state) {
case JMP_BUF_STATE_INITIALIZED: {
- RB_WASM_DEBUG_LOG("[%s] JMP_BUF_STATE_INITIALIZED\n", __func__);
+ RB_WASM_DEBUG_LOG(" JMP_BUF_STATE_INITIALIZED");
env->state = JMP_BUF_STATE_CAPTURING;
env->payload = 0;
_rb_wasm_active_jmpbuf = env;
@@ -76,14 +91,14 @@ _rb_wasm_setjmp_internal(rb_wasm_jmp_buf *env)
}
case JMP_BUF_STATE_CAPTURING: {
asyncify_stop_rewind();
- RB_WASM_DEBUG_LOG("[%s] JMP_BUF_STATE_CAPTURING\n", __func__);
+ RB_WASM_DEBUG_LOG(" JMP_BUF_STATE_CAPTURING");
env->state = JMP_BUF_STATE_CAPTURED;
_rb_wasm_active_jmpbuf = NULL;
return 0;
}
case JMP_BUF_STATE_RETURNING: {
asyncify_stop_rewind();
- RB_WASM_DEBUG_LOG("[%s] JMP_BUF_STATE_RETURNING\n", __func__);
+ RB_WASM_DEBUG_LOG(" JMP_BUF_STATE_RETURNING");
env->state = JMP_BUF_STATE_CAPTURED;
_rb_wasm_active_jmpbuf = NULL;
return env->payload;
@@ -97,7 +112,7 @@ _rb_wasm_setjmp_internal(rb_wasm_jmp_buf *env)
void
_rb_wasm_longjmp(rb_wasm_jmp_buf* env, int value)
{
- RB_WASM_DEBUG_LOG("[%s] env = %p, env->state = %d, value = %d\n", __func__, env, env->state, value);
+ RB_WASM_DEBUG_LOG("enter _rb_wasm_longjmp");
assert(env->state == JMP_BUF_STATE_CAPTURED);
assert(value != 0);
env->state = JMP_BUF_STATE_RETURNING;
@@ -179,20 +194,20 @@ rb_wasm_try_catch_loop_run(struct rb_wasm_try_catch *try_catch, rb_wasm_jmp_buf
void *
rb_wasm_handle_jmp_unwind(void)
{
- RB_WASM_DEBUG_LOG("[%s] _rb_wasm_active_jmpbuf = %p\n", __func__, _rb_wasm_active_jmpbuf);
+ RB_WASM_DEBUG_LOG("enter rb_wasm_handle_jmp_unwind");
if (!_rb_wasm_active_jmpbuf) {
return NULL;
}
switch (_rb_wasm_active_jmpbuf->state) {
case JMP_BUF_STATE_CAPTURING: {
- RB_WASM_DEBUG_LOG("[%s] JMP_BUF_STATE_CAPTURING\n", __func__);
+ RB_WASM_DEBUG_LOG(" JMP_BUF_STATE_CAPTURING");
// save the captured Asyncify stack top
_rb_wasm_active_jmpbuf->dst_buf_top = _rb_wasm_active_jmpbuf->setjmp_buf.top;
break;
}
case JMP_BUF_STATE_RETURNING: {
- RB_WASM_DEBUG_LOG("[%s] JMP_BUF_STATE_RETURNING\n", __func__);
+ RB_WASM_DEBUG_LOG(" JMP_BUF_STATE_RETURNING");
// restore the saved Asyncify stack top
_rb_wasm_active_jmpbuf->setjmp_buf.top = _rb_wasm_active_jmpbuf->dst_buf_top;
break;