Esempio n. 1
0
// request:
// 0: nothing
// 1: get state
// 3: throw sigint if `!defer_signal && io_wait` or if force throw threshold
//    is reached
void usr2_handler(int sig, siginfo_t *info, void *ctx)
{
    jl_tls_states_t *ptls = jl_get_ptls_states();
    sig_atomic_t request = jl_atomic_exchange(&ptls->signal_request, 0);
    if (request == 1) {
        signal_context = jl_to_bt_context(ctx);

        pthread_mutex_lock(&in_signal_lock);
        pthread_cond_broadcast(&signal_caught_cond);
        pthread_cond_wait(&exit_signal_cond, &in_signal_lock);
        request = jl_atomic_exchange(&ptls->signal_request, 0);
        assert(request == 1);
        (void)request;
        pthread_cond_broadcast(&signal_caught_cond);
        pthread_mutex_unlock(&in_signal_lock);
    }
    else if (request == 2) {
        jl_unblock_signal(sig);
        int force = jl_check_force_sigint();
        if (force || (!ptls->defer_signal && ptls->io_wait)) {
            jl_safepoint_consume_sigint();
            if (force)
                jl_safe_printf("WARNING: Force throwing a SIGINT\n");
            // Force a throw
            jl_clear_force_sigint();
            jl_throw_in_ctx(jl_interrupt_exception, ctx);
        }
    }
}
Esempio n. 2
0
static void jl_throw_in_ctx(jl_ptls_t ptls, jl_value_t *e, void *sigctx)
{
    if (!ptls->safe_restore)
        ptls->bt_size = rec_backtrace_ctx(ptls->bt_data, JL_MAX_BT_SIZE,
                                          jl_to_bt_context(sigctx));
    ptls->exception_in_transit = e;
    jl_call_in_ctx(ptls, &jl_rethrow, sigctx);
}
Esempio n. 3
0
static void JL_NORETURN jl_throw_in_ctx(jl_value_t *e, void *sigctx)
{
    if (!jl_safe_restore)
        jl_bt_size = rec_backtrace_ctx(jl_bt_data, JL_MAX_BT_SIZE,
                                       jl_to_bt_context(sigctx));
    jl_exception_in_transit = e;
    // TODO throw the error by modifying sigctx for supported platforms
    // This will avoid running the atexit handler on the signal stack
    // if no excepiton handler is registered.
    jl_rethrow();
}
Esempio n. 4
0
void sigdie_handler(int sig, siginfo_t *info, void *context)
{
    sigset_t sset;
    uv_tty_reset_mode();
    jl_critical_error(sig, jl_to_bt_context(context), jl_bt_data, &jl_bt_size);
    sigfillset(&sset);
    sigprocmask(SIG_UNBLOCK, &sset, NULL);
    signal(sig, SIG_DFL);
    if (sig != SIGSEGV &&
        sig != SIGBUS &&
        sig != SIGILL) {
        raise(sig);
    }
    // fall-through return to re-execute faulting statement (but without the error handler)
}
Esempio n. 5
0
// request:
// 0: nothing
// 1: get state
// 2: throw sigint if `!defer_signal && io_wait` or if force throw threshold
//    is reached
// 3: exit with `thread0_exit_state`
void usr2_handler(int sig, siginfo_t *info, void *ctx)
{
    jl_ptls_t ptls = jl_get_ptls_states();
    int errno_save = errno;
    sig_atomic_t request = jl_atomic_exchange(&ptls->signal_request, 0);
#if !defined(JL_DISABLE_LIBUNWIND)
    if (request == 1) {
        signal_context = jl_to_bt_context(ctx);

        pthread_mutex_lock(&in_signal_lock);
        pthread_cond_broadcast(&signal_caught_cond);
        pthread_cond_wait(&exit_signal_cond, &in_signal_lock);
        request = jl_atomic_exchange(&ptls->signal_request, 0);
        assert(request == 1);
        (void)request;
        pthread_cond_broadcast(&signal_caught_cond);
        pthread_mutex_unlock(&in_signal_lock);
    }
    else
#endif
    if (request == 2) {
        int force = jl_check_force_sigint();
        if (force || (!ptls->defer_signal && ptls->io_wait)) {
            jl_safepoint_consume_sigint();
            if (force)
                jl_safe_printf("WARNING: Force throwing a SIGINT\n");
            // Force a throw
            jl_clear_force_sigint();
            jl_throw_in_ctx(ptls, jl_interrupt_exception, sig, ctx);
        }
    }
    else if (request == 3) {
        jl_call_in_ctx(ptls, jl_exit_thread0_cb, sig, ctx);
    }
    errno = errno_save;
}