/*******************************************************************************
 * Copyright (c) 2007, 2015 Wind River Systems, Inc. and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * and Eclipse Distribution License v1.0 which accompany this distribution.
 * The Eclipse Public License is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * and the Eclipse Distribution License is available at
 * http://www.eclipse.org/org/documents/edl-v10.php.
 * You may elect to redistribute this code under either of these licenses.
 *
 * Contributors:
 *     Wind River Systems - initial API and implementation
 *******************************************************************************/

/*
 * Target service implementation: run control (TCF name RunControl)
 */

#include <tcf/config.h>

#if SERVICE_RunControl

#include <stdlib.h>
#include <string.h>
#include <signal.h>
#include <errno.h>
#include <assert.h>
#include <tcf/framework/protocol.h>
#include <tcf/framework/channel.h>
#include <tcf/framework/json.h>
#include <tcf/framework/context.h>
#include <tcf/framework/myalloc.h>
#include <tcf/framework/trace.h>
#include <tcf/framework/events.h>
#include <tcf/framework/exceptions.h>
#include <tcf/framework/signames.h>
#include <tcf/framework/cache.h>
#include <tcf/services/runctrl.h>
#include <tcf/services/contextquery.h>
#include <tcf/services/breakpoints.h>
#include <tcf/services/linenumbers.h>
#include <tcf/services/stacktrace.h>
#include <tcf/services/diagnostics.h>
#include <tcf/services/symbols.h>
#include <tcf/main/cmdline.h>

#define EN_STEP_OVER (SERVICE_Breakpoints && SERVICE_StackTrace && ENABLE_Symbols)
#define EN_STEP_LINE (ENABLE_LineNumbers)

#define STOP_ALL_TIMEOUT 1000000
#define STOP_ALL_MAX_CNT 20

#ifndef RC_STEP_MAX_STACK_FRAMES
#define RC_STEP_MAX_STACK_FRAMES 10000
#endif

typedef struct Listener {
    RunControlEventListener * listener;
    void * args;
} Listener;

static Listener * listeners = NULL;
static unsigned listener_cnt = 0;
static unsigned listener_max = 0;

static const char RUN_CONTROL[] = "RunControl";

typedef struct ContextExtensionRC {
    int pending_safe_event; /* safe events are waiting for this context to be stopped */
    int intercepted;        /* context is reported to a host as suspended */
    int intercept_group;
    int reverse_run;
    int step_mode;
    int step_cnt;
    int step_line_cnt;
    int stop_group_mark;
    int run_ctrl_ctx_lock_cnt;
    ContextAddress step_range_start;
    ContextAddress step_range_end;
    ContextAddress step_frame_fp;
    ContextAddress step_bp_addr;
    BreakpointInfo * step_bp_info;
    int step_inlined;
    int step_chk_inline_frame;
    CodeArea * step_code_area;
    ErrorReport * step_error;
    const char * step_done;
    Channel * step_channel;
    int step_continue_mode;
    int safe_single_step;   /* not zero if the context is performing a "safe" single instruction step */
    int cannot_stop;
    ContextAddress pc;
    int pc_error;
    char * state_name;
    char ** bp_ids;
    unsigned bp_cnt;
    unsigned bp_max;
    int skip_prologue;
    LINK link;
} ContextExtensionRC;

static size_t context_extension_offset = 0;

#define EXT(ctx) (ctx ? ((ContextExtensionRC *)((char *)(ctx) + context_extension_offset)) : NULL)
#define link2ctx(lnk) ((Context *)((char *)(lnk) - offsetof(ContextExtensionRC, link) - context_extension_offset))

typedef struct SafeEvent {
    Context * ctx;
    EventCallBack * done;
    void * arg;
    struct SafeEvent * next;
} SafeEvent;

typedef struct GetContextArgs {
    Channel * c;
    char token[256];
    Context * ctx;
} GetContextArgs;

static SafeEvent * safe_event_list = NULL;
static SafeEvent * safe_event_last = NULL;
static int safe_event_active = 0;
static int safe_event_pid_count = 0;
static int run_ctrl_lock_cnt = 0;
static int stop_all_timer_cnt = 0;
static int stop_all_timer_posted = 0;
static int run_safe_events_posted = 0;

static AbstractCache safe_events_cache;

static TCFBroadcastGroup * broadcast_group = NULL;

static void run_safe_events(void * arg);

static int get_resume_modes(Context * ctx) {
    int md, modes;
    int has_state = context_has_state(ctx);

    modes = 0;
    for (md = 0; md < RM_UNDEF; md++) {
        if (md == RM_DETACH) continue;
        if (md == RM_TERMINATE) continue;
        if (context_can_resume(ctx, md)) modes |= 1 << md;
    }
    if (!has_state) {
        modes &= (1 << RM_RESUME) | (1 << RM_REVERSE_RESUME);
    }
    else {
        if (modes & (1 << RM_STEP_INTO)) {
            modes |= (1 << RM_STEP_INTO_RANGE);
#if EN_STEP_OVER
            modes |= (1 << RM_STEP_OVER);
            modes |= (1 << RM_STEP_OVER_RANGE);
            modes |= (1 << RM_STEP_OUT);
#endif
#if EN_STEP_LINE
            modes |= (1 << RM_STEP_INTO_LINE);
#endif
#if EN_STEP_OVER && EN_STEP_LINE
            modes |= (1 << RM_STEP_OVER_LINE);
#endif
        }
        if (modes & (1 << RM_REVERSE_STEP_INTO)) {
            modes |= (1 << RM_REVERSE_STEP_INTO_RANGE);
#if EN_STEP_OVER
            modes |= (1 << RM_REVERSE_STEP_OVER);
            modes |= (1 << RM_REVERSE_STEP_OVER_RANGE);
            modes |= (1 << RM_REVERSE_STEP_OUT);
#endif
#if EN_STEP_LINE
            modes |= (1 << RM_REVERSE_STEP_INTO_LINE);
#endif
#if EN_STEP_OVER && EN_STEP_LINE
            modes |= (1 << RM_REVERSE_STEP_OVER_LINE);
#endif
        }
    }
    return modes;
}

static void write_context(OutputStream * out, Context * ctx) {
    int modes;
    Context * rc_grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
    Context * bp_grp = context_get_group(ctx, CONTEXT_GROUP_BREAKPOINT);
    Context * ss_grp = context_get_group(ctx, CONTEXT_GROUP_SYMBOLS);
    Context * cpu_grp = context_get_group(ctx, CONTEXT_GROUP_CPU);

    assert(!ctx->exited);

    write_stream(out, '{');

    json_write_string(out, "ID");
    write_stream(out, ':');
    json_write_string(out, ctx->id);

    if (ctx->parent != NULL) {
        write_stream(out, ',');
        json_write_string(out, "ParentID");
        write_stream(out, ':');
        json_write_string(out, ctx->parent->id);
    }

    if (ctx->creator != NULL) {
        write_stream(out, ',');
        json_write_string(out, "CreatorID");
        write_stream(out, ':');
        json_write_string(out, ctx->creator->id);
    }

    write_stream(out, ',');
    json_write_string(out, "ProcessID");
    write_stream(out, ':');
    json_write_string(out, context_get_group(ctx, CONTEXT_GROUP_PROCESS)->id);

    if (ctx->name != NULL) {
        write_stream(out, ',');
        json_write_string(out, "Name");
        write_stream(out, ':');
        json_write_string(out, ctx->name);
    }

    write_stream(out, ',');
    json_write_string(out, "CanSuspend");
    write_stream(out, ':');
    json_write_boolean(out, 1);

    write_stream(out, ',');
    json_write_string(out, "CanResume");
    write_stream(out, ':');
    modes = get_resume_modes(ctx);
    json_write_long(out, modes);

    if (context_has_state(ctx)) {
        write_stream(out, ',');
        json_write_string(out, "HasState");
        write_stream(out, ':');
        json_write_boolean(out, 1);
    }
    else {
        write_stream(out, ',');
        json_write_string(out, "IsContainer");
        write_stream(out, ':');
        json_write_boolean(out, 1);
    }

    write_stream(out, ',');
    json_write_string(out, "WordSize");
    write_stream(out, ':');
    json_write_long(out, context_word_size(ctx));

    if (context_can_resume(ctx, RM_TERMINATE)) {
        write_stream(out, ',');
        json_write_string(out, "CanTerminate");
        write_stream(out, ':');
        json_write_boolean(out, 1);
    }

    if (context_can_resume(ctx, RM_DETACH)) {
        write_stream(out, ',');
        json_write_string(out, "CanDetach");
        write_stream(out, ':');
        json_write_boolean(out, 1);
    }

    if (rc_grp != NULL) {
        write_stream(out, ',');
        json_write_string(out, "RCGroup");
        write_stream(out, ':');
        json_write_string(out, rc_grp->id);
    }

    if (bp_grp != NULL) {
        write_stream(out, ',');
        json_write_string(out, "BPGroup");
        write_stream(out, ':');
        json_write_string(out, bp_grp->id);
    }

    if (ss_grp != NULL) {
        write_stream(out, ',');
        json_write_string(out, "SymbolsGroup");
        write_stream(out, ':');
        json_write_string(out, ss_grp->id);
    }

    if (cpu_grp != NULL) {
        write_stream(out, ',');
        json_write_string(out, "CPUGroup");
        write_stream(out, ':');
        json_write_string(out, cpu_grp->id);
    }

#if ENABLE_RCBP_TEST
    if (is_test_process(ctx)) {
        write_stream(out, ',');
        json_write_string(out, "DiagnosticTestProcess");
        write_stream(out, ':');
        json_write_boolean(out, 1);
    }
#endif

    if (ctx->big_endian) {
        write_stream(out, ',');
        json_write_string(out, "BigEndian");
        write_stream(out, ':');
        json_write_boolean(out, 1);
    }

#if ENABLE_ContextExtraProperties
    {
        /* Back-end context properties */
        int cnt = 0;
        const char ** names = NULL;
        const char ** values = NULL;
        if (context_get_extra_properties(ctx, &names, &values, &cnt) == 0) {
            while (cnt > 0) {
                if (*values != NULL) {
                    write_stream(out, ',');
                    json_write_string(out, *names);
                    write_stream(out, ':');
                    write_string(out, *values);
                }
                names++;
                values++;
                cnt--;
            }
        }
    }
#endif

    write_stream(out, '}');
}

static void get_current_pc(Context * ctx) {
    size_t i;
    uint8_t buf[8];
    ContextExtensionRC * ext = EXT(ctx);
    RegisterDefinition * def = get_PC_definition(ctx);
    ext->pc = 0;
    ext->pc_error = 0;
    if (def == NULL) {
        ext->pc_error = set_errno(ERR_OTHER, "Program counter register not found");
        return;
    }
    if (!ctx->stopped) {
        ext->pc_error = ERR_IS_RUNNING;
        return;
    }
    assert(def->size <= sizeof(buf));
    if (context_read_reg(ctx, def, 0, def->size, buf) < 0) {
        ext->pc_error = errno;
        return;
    }
    for (i = 0; i < def->size; i++) {
        ext->pc = ext->pc << 8;
        ext->pc |= buf[def->big_endian ? i : def->size - i - 1];
    }
}

#if ENABLE_ContextStateProperties
static int is_json(const char * s) {
    Trap trap;
    if (set_trap(&trap)) {
        ByteArrayInputStream buf;
        InputStream * inp = create_byte_array_input_stream(&buf, s, strlen(s));
        json_skip_object(inp);
        if (read_stream(inp) != MARKER_EOS) exception(ERR_JSON_SYNTAX);
        clear_trap(&trap);
    }
    return trap.error == 0;
}
#endif

static const char * get_suspend_reason(Context * ctx) {
    const char * reason = NULL;
    ContextExtensionRC * ext = EXT(ctx);
    if (ext->bp_cnt > 0) return REASON_BREAKPOINT;
    if (ctx->exception_description != NULL) return ctx->exception_description;
    if (ext->step_error != NULL) return errno_to_str(set_error_report_errno(ext->step_error));
    if (ext->step_done != NULL) return ext->step_done;
    reason = context_suspend_reason(ctx);
    if (reason != NULL)  return reason;
    return REASON_USER_REQUEST;
}

static void write_context_state(OutputStream * out, Context * ctx) {
    int fst = 1;
    ContextExtensionRC * ext = EXT(ctx);

    assert(!ctx->exited);

    if (!ext->intercepted) {
        write_stringz(out, "0");
        write_stringz(out, "null");
    }
    else {

        /* Number: PC */
        json_write_uint64(out, ext->pc);
        write_stream(out, 0);

        /* String: Reason */
        json_write_string(out, get_suspend_reason(ctx));
        write_stream(out, 0);
    }

    /* Object: Additional context state info */
    write_stream(out, '{');
    if (ext->intercepted) {
        if (ext->step_error == NULL && ext->step_done == NULL && ctx->signal) {
            const char * name = signal_name(ctx->signal);
            const char * desc = signal_description(ctx->signal);
            json_write_string(out, "Signal");
            write_stream(out, ':');
            json_write_long(out, ctx->signal);
            if (name != NULL) {
                write_stream(out, ',');
                json_write_string(out, "SignalName");
                write_stream(out, ':');
                json_write_string(out, name);
            }
            if (desc != NULL) {
                write_stream(out, ',');
                json_write_string(out, "SignalDescription");
                write_stream(out, ':');
                json_write_string(out, desc);
            }
            fst = 0;
        }
        if (ext->bp_cnt > 0) {
            unsigned i = 0;
            if (!fst) write_stream(out, ',');
            json_write_string(out, "BPs");
            write_stream(out, ':');
            write_stream(out, '[');
            for (i = 0; i < ext->bp_cnt; i++) {
                if (i > 0) write_stream(out, ',');
                json_write_string(out, ext->bp_ids[i]);
            }
            write_stream(out, ']');
            fst = 0;
        }
        if (ext->pc_error) {
            if (!fst) write_stream(out, ',');
            json_write_string(out, "PCError");
            write_stream(out, ':');
            write_error_object(out, ext->pc_error);
            fst = 0;
        }
        if (ext->step_error != NULL) {
            if (!fst) write_stream(out, ',');
            json_write_string(out, "StepError");
            write_stream(out, ':');
            write_error_object(out, set_error_report_errno(ext->step_error));
            fst = 0;
        }
        if (ctx->stopped_by_funccall) {
            if (!fst) write_stream(out, ',');
            json_write_string(out, "FuncCall");
            write_stream(out, ':');
            json_write_boolean(out, 1);
            fst = 0;
        }
    }
    else {
        if (ext->state_name != NULL) {
            json_write_string(out, "StateName");
            write_stream(out, ':');
            json_write_string(out, ext->state_name);
            fst = 0;
        }
    }
#if ENABLE_ContextStateProperties
    {
        /* Back-end context state properties */
        int cnt = 0;
        const char ** names = NULL;
        const char ** values = NULL;
        if (context_get_state_properties(ctx, &names, &values, &cnt) == 0) {
            while (cnt > 0) {
                if (*values != NULL) {
                    if (!fst) write_stream(out, ',');
                    json_write_string(out, *names);
                    write_stream(out, ':');
                    /* In older versions of the API, value was a simple string.
                     * Latest version requires it to be in JSON.
                     * For backward compatibility, check if the value is in JSON. */
                    if (is_json(*values)) write_string(out, *values);
                    else json_write_string(out, *values);
                    fst = 0;
                }
                names++;
                values++;
                cnt--;
            }
        }
    }
#endif
    write_stream(out, '}');
    write_stream(out, 0);
}

static void command_get_context(char * token, Channel * c) {
    int err = 0;
    char id[256];
    Context * ctx = NULL;

    json_read_string(&c->inp, id, sizeof(id));
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    ctx = id2ctx(id);

    if (ctx == NULL) err = ERR_INV_CONTEXT;
    else if (ctx->exited) err = ERR_ALREADY_EXITED;

    write_stringz(&c->out, "R");
    write_stringz(&c->out, token);
    write_errno(&c->out, err);
    if (err == 0) {
        write_context(&c->out, ctx);
        write_stream(&c->out, 0);
    }
    else {
        write_stringz(&c->out, "null");
    }
    write_stream(&c->out, MARKER_EOM);
}

static void command_get_children(char * token, Channel * c) {
    char id[256];

    json_read_string(&c->inp, id, sizeof(id));
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    write_stringz(&c->out, "R");
    write_stringz(&c->out, token);

    write_errno(&c->out, 0);

    write_stream(&c->out, '[');
    if (id[0] == 0) {
        LINK * l;
        int cnt = 0;
        for (l = context_root.next; l != &context_root; l = l->next) {
            Context * ctx = ctxl2ctxp(l);
            if (ctx->parent != NULL) continue;
            if (ctx->exited) continue;
            if (cnt > 0) write_stream(&c->out, ',');
            json_write_string(&c->out, ctx->id);
            cnt++;
        }
    }
    else {
        Context * parent = id2ctx(id);
        if (parent != NULL) {
            LINK * l;
            int cnt = 0;
            for (l = parent->children.next; l != &parent->children; l = l->next) {
                Context * ctx = cldl2ctxp(l);
                assert(ctx->parent == parent);
                if (ctx->exited) continue;
                if (cnt > 0) write_stream(&c->out, ',');
                json_write_string(&c->out, ctx->id);
                cnt++;
            }
        }
    }
    write_stream(&c->out, ']');
    write_stream(&c->out, 0);

    write_stream(&c->out, MARKER_EOM);
}

typedef struct CommandGetStateArgs {
    char token[256];
    char id[256];
} CommandGetStateArgs;

static void command_get_state_cache_client(void * x) {
    CommandGetStateArgs * args = (CommandGetStateArgs *)x;
    Context * ctx = NULL;
    ContextExtensionRC * ext = NULL;
    Channel * c = cache_channel();
    int err = 0;

    ctx = id2ctx(args->id);
    if (ctx != NULL) ext = EXT(ctx);

    if (ctx == NULL || !context_has_state(ctx)) err = ERR_INV_CONTEXT;
    else if (ctx->exited) err = ERR_ALREADY_EXITED;

    if (ext != NULL) get_current_pc(ctx);

    cache_exit();

    write_stringz(&c->out, "R");
    write_stringz(&c->out, args->token);

    write_errno(&c->out, err);

    json_write_boolean(&c->out, ext != NULL && ext->intercepted);
    write_stream(&c->out, 0);

    if (err) {
        write_stringz(&c->out, "0");
        write_stringz(&c->out, "null");
        write_stringz(&c->out, "null");
    }
    else {
        write_context_state(&c->out, ctx);
    }

    write_stream(&c->out, MARKER_EOM);
}

static void command_get_state(char * token, Channel * c) {
    CommandGetStateArgs args;

    memset(&args, 0, sizeof(args));
    json_read_string(&c->inp, args.id, sizeof(args.id));
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    strlcpy(args.token, token, sizeof(args.token));
    cache_enter(command_get_state_cache_client, c, &args, sizeof(args));
}

#if ENABLE_ContextISA

typedef struct CommandGetISAArgs {
    char token[256];
    char id[256];
    ContextAddress addr;
} CommandGetISAArgs;

static void command_get_isa_cache_client(void * x) {
    CommandGetISAArgs * args = (CommandGetISAArgs *)x;
    Context * ctx = NULL;
    Channel * c = cache_channel();
    ContextISA isa;
    int err = 0;

    ctx = id2ctx(args->id);

    memset(&isa, 0, sizeof(isa));
    if (ctx == NULL) err = ERR_INV_CONTEXT;
    else if (ctx->exited) err = ERR_ALREADY_EXITED;
    else if (context_get_isa(ctx, args->addr, &isa) < 0) err = errno;

    cache_exit();

    write_stringz(&c->out, "R");
    write_stringz(&c->out, args->token);

    write_errno(&c->out, err);

    if (err) {
        write_stringz(&c->out, "null");
    }
    else {
        write_stream(&c->out, '{');
        json_write_string(&c->out, "Addr");
        write_stream(&c->out, ':');
        json_write_uint64(&c->out, isa.addr);
        write_stream(&c->out, ',');
        json_write_string(&c->out, "Size");
        write_stream(&c->out, ':');
        json_write_uint64(&c->out, isa.size);
        write_stream(&c->out, ',');
        json_write_string(&c->out, "Alignment");
        write_stream(&c->out, ':');
        json_write_uint64(&c->out, isa.alignment);
        write_stream(&c->out, ',');
        json_write_string(&c->out, "MaxInstrSize");
        write_stream(&c->out, ':');
        json_write_uint64(&c->out, isa.max_instruction_size);
        if (isa.def != NULL) {
            write_stream(&c->out, ',');
            json_write_string(&c->out, "DefISA");
            write_stream(&c->out, ':');
            json_write_string(&c->out, isa.def);
        }
        if (isa.isa != NULL) {
            write_stream(&c->out, ',');
            json_write_string(&c->out, "ISA");
            write_stream(&c->out, ':');
            json_write_string(&c->out, isa.isa);
        }
        write_stream(&c->out, '}');
        write_stream(&c->out, 0);
    }

    write_stream(&c->out, MARKER_EOM);
}

static void command_get_isa(char * token, Channel * c) {
    CommandGetISAArgs args;

    memset(&args, 0, sizeof(args));
    json_read_string(&c->inp, args.id, sizeof(args.id));
    json_test_char(&c->inp, MARKER_EOA);
    args.addr = (ContextAddress)json_read_uint64(&c->inp);
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    strlcpy(args.token, token, sizeof(args.token));
    cache_enter(command_get_isa_cache_client, c, &args, sizeof(args));
}

#endif /* ENABLE_ContextISA */

static void send_simple_result(Channel * c, char * token, int err) {
    write_stringz(&c->out, "R");
    write_stringz(&c->out, token);
    write_errno(&c->out, err);
    write_stream(&c->out, MARKER_EOM);
}

static void send_event_context_resumed(Context * ctx);

typedef struct ResumeParams {
    ContextAddress range_start;
    ContextAddress range_end;
    int error;
} ResumeParams;

static void resume_params_callback(InputStream * inp, const char * name, void * x) {
    ResumeParams * args = (ResumeParams *)x;
    if (strcmp(name, "RangeStart") == 0) args->range_start = (ContextAddress)json_read_uint64(inp);
    else if (strcmp(name, "RangeEnd") == 0) args->range_end = (ContextAddress)json_read_uint64(inp);
    else {
        json_skip_object(inp);
        args->error = ERR_UNSUPPORTED;
    }
}

static int resume_context_tree(Context * ctx) {
    if (!context_has_state(ctx)) {
        LINK * l;
        for (l = ctx->children.next; l != &ctx->children; l = l->next) {
            Context * x = cldl2ctxp(l);
            if (!x->exited) resume_context_tree(x);
        }
    }
    else if (EXT(ctx)->intercepted) {
        Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
        send_event_context_resumed(grp);
        assert(!EXT(ctx)->intercepted);
        if (run_ctrl_lock_cnt == 0 && run_safe_events_posted < 4) {
            run_safe_events_posted++;
            post_event(run_safe_events, NULL);
        }
    }
    return 0;
}

static void free_code_area(CodeArea * area) {
    loc_free(area->directory);
    loc_free(area->file);
    loc_free(area);
}

static void cancel_step_mode(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);

    if (ext->step_channel) {
        channel_unlock_with_msg(ext->step_channel, RUN_CONTROL);
        ext->step_channel = NULL;
    }
    if (ext->step_bp_info != NULL) {
        destroy_eventpoint(ext->step_bp_info);
        ext->step_bp_info = NULL;
    }
    if (ext->step_code_area != NULL) {
        free_code_area(ext->step_code_area);
        ext->step_code_area = NULL;
    }
    ext->step_cnt = 0;
    ext->step_line_cnt = 0;
    ext->step_range_start = 0;
    ext->step_range_end = 0;
    ext->step_frame_fp = 0;
    ext->step_bp_addr = 0;
    ext->step_inlined = 0;
    ext->step_chk_inline_frame = 0;
    ext->step_continue_mode = RM_RESUME;
    ext->step_mode = RM_RESUME;
}

static void start_step_mode(Context * ctx, Channel * c, int mode, ContextAddress range_start, ContextAddress range_end) {
    ContextExtensionRC * ext = EXT(ctx);

    cancel_step_mode(ctx);
    if (ext->step_error) {
        release_error_report(ext->step_error);
        ext->step_error = NULL;
    }
    assert(ext->step_channel == NULL);
    if (mode == RM_RESUME || mode == RM_REVERSE_RESUME ||
        mode == RM_TERMINATE || mode == RM_DETACH) c = NULL;
    if (c != NULL) {
        ext->step_channel = c;
        channel_lock_with_msg(ext->step_channel, RUN_CONTROL);
    }
    ext->step_done = NULL;
    ext->step_mode = mode;
    ext->step_range_start = range_start;
    ext->step_range_end = range_end;
}

int continue_debug_context(Context * ctx, Channel * c,
        int mode, int count, ContextAddress range_start, ContextAddress range_end) {
    ContextExtensionRC * ext = EXT(ctx);
    Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
    int err = 0;

    EXT(grp)->reverse_run = 0;
    switch (mode) {
    case RM_REVERSE_RESUME:
    case RM_REVERSE_STEP_OVER:
    case RM_REVERSE_STEP_INTO:
    case RM_REVERSE_STEP_OVER_LINE:
    case RM_REVERSE_STEP_INTO_LINE:
    case RM_REVERSE_STEP_OUT:
    case RM_REVERSE_STEP_OVER_RANGE:
    case RM_REVERSE_STEP_INTO_RANGE:
    case RM_REVERSE_UNTIL_ACTIVE:
        EXT(grp)->reverse_run = 1;
        break;
    }

    if (context_has_state(ctx)) start_step_mode(ctx, c, mode, range_start, range_end);

    if (ctx->exited) {
        err = ERR_ALREADY_EXITED;
    }
    else if (context_has_state(ctx) && !ext->intercepted) {
        err = ERR_ALREADY_RUNNING;
    }
    else if (count != 1) {
        err = EINVAL;
    }
    else if (resume_context_tree(ctx) < 0) {
        err = errno;
    }

    assert(err || !ext->intercepted);
    if (err) {
        cancel_step_mode(ctx);
        errno = err;
        return -1;
    }

    return 0;
}

static void command_resume(char * token, Channel * c) {
    char id[256];
    int mode;
    long count;
    int err = 0;
    ResumeParams args;
    Context * ctx = NULL;

    memset(&args, 0, sizeof(args));
    json_read_string(&c->inp, id, sizeof(id));
    json_test_char(&c->inp, MARKER_EOA);
    mode = (int)json_read_long(&c->inp);
    json_test_char(&c->inp, MARKER_EOA);
    count = json_read_long(&c->inp);
    json_test_char(&c->inp, MARKER_EOA);
    if (peek_stream(&c->inp) != MARKER_EOM) {
        json_read_struct(&c->inp, resume_params_callback, &args);
        json_test_char(&c->inp, MARKER_EOA);
        err = args.error;
    }
    json_test_char(&c->inp, MARKER_EOM);

    if (err == 0 && (ctx = id2ctx(id)) == NULL) err = ERR_INV_CONTEXT;
    if (err == 0 && ((mode >= RM_UNDEF) || ((get_resume_modes(ctx) & (1 << mode)) == 0))) err = EINVAL;
    if (err == 0 && continue_debug_context(ctx, c, mode, count, args.range_start, args.range_end) < 0) err = errno;
    send_simple_result(c, token, err);
}

int suspend_debug_context(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);

    if (ctx->exited) {
        /* do nothing */
    }
    else if (context_has_state(ctx)) {
        assert(!ctx->stopped || !ext->safe_single_step);
        if (!ctx->stopped) {
            assert(!ext->intercepted);
            if (!ctx->exiting) {
                ctx->pending_intercept = 1;
                if (!ext->safe_single_step && context_stop(ctx) < 0) return -1;
            }
        }
        else if (!ext->intercepted) {
            ctx->pending_intercept = 1;
            if (run_ctrl_lock_cnt == 0 && run_safe_events_posted < 4) {
                run_safe_events_posted++;
                post_event(run_safe_events, NULL);
            }
        }
    }
    else {
        LINK * l;
        for (l = ctx->children.next; l != &ctx->children; l = l->next) {
            suspend_debug_context(cldl2ctxp(l));
        }
    }
    return 0;
}

int suspend_by_breakpoint(Context * ctx, Context * trigger, const char * bp, int skip_prologue) {
    ContextExtensionRC * ext = EXT(ctx);

    if (ctx->exited) {
        /* do nothing */
    }
    else if (context_has_state(ctx)) {
        assert(!ctx->stopped || !ext->safe_single_step);
        if (!ext->intercepted && bp != NULL && ctx == trigger) {
            unsigned i = 0;
            while (i < ext->bp_cnt && strcmp(ext->bp_ids[i], bp)) i++;
            if (i >= ext->bp_cnt) {
                if (ext->bp_cnt + 2 > ext->bp_max) {
                    ext->bp_max += 8;
                    ext->bp_ids = (char **)loc_realloc(ext->bp_ids, ext->bp_max * sizeof(char *));
                }
                ext->bp_ids[ext->bp_cnt++] = loc_strdup(bp);
                ext->bp_ids[ext->bp_cnt] = NULL;
            }
        }
        if (!ctx->stopped) {
            assert(!ext->intercepted);
            if (!ctx->exiting) {
                if (skip_prologue) ext->skip_prologue = 1;
                else ctx->pending_intercept = 1;
                if (!ext->safe_single_step && context_stop(ctx) < 0) return -1;
            }
        }
        else if (!ext->intercepted) {
            if (skip_prologue) ext->skip_prologue = 1;
            else ctx->pending_intercept = 1;
            if (run_ctrl_lock_cnt == 0 && run_safe_events_posted < 4) {
                run_safe_events_posted++;
                post_event(run_safe_events, NULL);
            }
        }
    }
    else {
        LINK * l;
        for (l = ctx->children.next; l != &ctx->children; l = l->next) {
            suspend_by_breakpoint(cldl2ctxp(l), trigger, bp, skip_prologue);
        }
    }
    return 0;
}

char ** get_context_breakpoint_ids(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    if (!ext->intercepted) return NULL;
    if (ext->bp_cnt == 0) return NULL;
    return ext->bp_ids;
}

typedef struct CommandSuspendArgs {
    char token[256];
    char id[256];
} CommandSuspendArgs;

static void command_suspend_cache_client(void * x) {
    CommandSuspendArgs * args = (CommandSuspendArgs *)x;
    Channel * c = cache_channel();
    Context * ctx = NULL;
    int err = 0;

    ctx = id2ctx(args->id);

    if (ctx == NULL) {
        err = ERR_INV_CONTEXT;
    }
    else if (ctx->exited) {
        err = ERR_ALREADY_EXITED;
    }
    else {
        ContextExtensionRC * ext = EXT(ctx);
        if (ext->intercepted) {
            err = ERR_ALREADY_STOPPED;
        }
        else if (suspend_debug_context(ctx) < 0) {
            err = errno;
        }
    }

    cache_exit();

    send_simple_result(c, args->token, err);
}

static void command_suspend(char * token, Channel * c) {
    CommandSuspendArgs args;

    memset(&args, 0, sizeof(args));
    json_read_string(&c->inp, args.id, sizeof(args.id));
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    strlcpy(args.token, token, sizeof(args.token));
    cache_enter(command_suspend_cache_client, c, &args, sizeof(args));
}

static void terminate_context_tree(Context * ctx) {
    if (ctx->exited) return;
    if (context_can_resume(ctx, RM_TERMINATE)) {
        ContextExtensionRC * ext = EXT(ctx);
        cancel_step_mode(ctx);
        ctx->pending_intercept = 0;
        ext->step_mode = RM_TERMINATE;
        resume_context_tree(ctx);
    }
    else if (EXT(ctx)->intercepted) {
        ContextExtensionRC * ext = EXT(ctx);
        cancel_step_mode(ctx);
        ctx->pending_intercept = 0;
        ext->step_mode = RM_RESUME;
        resume_context_tree(ctx);
    }
    else {
        LINK * l = ctx->children.next;
        while (l != &ctx->children) {
            Context * x = cldl2ctxp(l);
            terminate_context_tree(x);
            l = l->next;
        }
    }
}

static void event_terminate(void * args) {
    Context * ctx = (Context *)args;
    terminate_context_tree(ctx);
    context_unlock(ctx);
}

int terminate_debug_context(Context * ctx) {
    int err = 0;
    if (ctx == NULL) {
        err = ERR_INV_CONTEXT;
    }
    else if (ctx->exited) {
        err = ERR_ALREADY_EXITED;
    }
    else {
        context_lock(ctx);
        post_safe_event(ctx, event_terminate, ctx);
    }
    if (err) {
        errno = err;
        return -1;
    }
    return 0;
}

static void command_terminate(char * token, Channel * c) {
    char id[256];
    int err = 0;

    json_read_string(&c->inp, id, sizeof(id));
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    if (terminate_debug_context(id2ctx(id)) != 0) err = errno;

    send_simple_result(c, token, err);
}

static void detach_context_tree(Context * ctx) {
    if (ctx->exited) return;
    if (context_can_resume(ctx, RM_DETACH)) {
        ContextExtensionRC * ext = EXT(ctx);
        cancel_step_mode(ctx);
        ctx->pending_intercept = 0;
        ext->step_mode = RM_DETACH;
        resume_context_tree(ctx);
    }
    else {
        LINK * l = ctx->children.next;
        while (l != &ctx->children) {
            Context * x = cldl2ctxp(l);
            detach_context_tree(x);
            l = l->next;
        }
    }
}

static void event_detach(void * args) {
    Context * ctx = (Context *)args;
    detach_context_tree(ctx);
    context_unlock(ctx);
}

int detach_debug_context(Context * ctx) {
    int err = 0;
    if (ctx == NULL) {
        err = ERR_INV_CONTEXT;
    }
    else if (ctx->exited) {
        err = ERR_ALREADY_EXITED;
    }
    else {
        context_lock(ctx);
        post_safe_event(ctx, event_detach, ctx);
    }
    if (err) {
        errno = err;
        return -1;
    }
    return 0;
}

static void command_detach(char * token, Channel * c) {
    char id[256];
    int err = 0;

    json_read_string(&c->inp, id, sizeof(id));
    json_test_char(&c->inp, MARKER_EOA);
    json_test_char(&c->inp, MARKER_EOM);

    if (detach_debug_context(id2ctx(id)) != 0) err = errno;

    send_simple_result(c, token, err);
}

static void notify_context_released(Context * ctx) {
    unsigned i;
    ContextExtensionRC * ext = EXT(ctx);
    assert(ext->intercepted);
    ext->intercepted = 0;
    ext->skip_prologue = 0;
    while (ext->bp_cnt > 0) loc_free(ext->bp_ids[--ext->bp_cnt]);
    for (i = 0; i < listener_cnt; i++) {
        Listener * l = listeners + i;
        if (l->listener->context_released == NULL) continue;
        l->listener->context_released(ctx, l->args);
    }
}

static void send_event_context_added(Context * ctx) {
    OutputStream * out = &broadcast_group->out;

    write_stringz(out, "E");
    write_stringz(out, RUN_CONTROL);
    write_stringz(out, "contextAdded");

    /* <array of context data> */
    write_stream(out, '[');
    write_context(out, ctx);
    write_stream(out, ']');
    write_stream(out, 0);

    write_stream(out, MARKER_EOM);
}

static void send_event_context_changed(Context * ctx) {
    OutputStream * out = &broadcast_group->out;

    write_stringz(out, "E");
    write_stringz(out, RUN_CONTROL);
    write_stringz(out, "contextChanged");

    /* <array of context data> */
    write_stream(out, '[');
    write_context(out, ctx);
    write_stream(out, ']');
    write_stream(out, 0);

    write_stream(out, MARKER_EOM);
}

static void send_event_context_removed(Context * ctx) {
    OutputStream * out = &broadcast_group->out;
    ContextExtensionRC * ext = EXT(ctx);

    if (ext->intercepted) notify_context_released(ctx);

    write_stringz(out, "E");
    write_stringz(out, RUN_CONTROL);
    write_stringz(out, "contextRemoved");

    /* <array of context IDs> */
    write_stream(out, '[');
    json_write_string(out, ctx->id);
    write_stream(out, ']');
    write_stream(out, 0);

    write_stream(out, MARKER_EOM);
}

static void send_event_context_suspended(void) {
    LINK p0; /* List of contexts intercepted by breakpoint or exception */
    LINK p1; /* List of all other intercepted contexts */
    LINK p2; /* List for notify_context_intercepted() */
    LINK * l = context_root.next;
    unsigned i;

    list_init(&p0);
    list_init(&p1);
    list_init(&p2);

    while (l != &context_root) {
        Context * ctx = ctxl2ctxp(l);
        l = l->next;
        if (ctx->pending_intercept && ctx->stopped) {
            LINK * n = &p1;
            ContextExtensionRC * ext = EXT(ctx);
            assert(!ctx->exited);
            assert(!ext->intercepted);
            assert(!ext->safe_single_step);
            cancel_step_mode(ctx);
            assert(!ext->intercepted);
            ext->intercepted = 1;
            ctx->pending_intercept = 0;
            if (strcmp(get_suspend_reason(ctx), REASON_USER_REQUEST)) n = &p0;
            list_add_last(&ext->link, n);
        }
    }

    while (!list_is_empty(&p0) || !list_is_empty(&p1)) {
        OutputStream * out = &broadcast_group->out;
        LINK * n = !list_is_empty(&p0) ? p0.next : p1.next;
        Context * ctx = link2ctx(n);
        int container = list_is_empty(&p0) && p1.next != p1.prev;

        list_remove(n);
        list_add_last(n, &p2);

        write_stringz(out, "E");
        write_stringz(out, RUN_CONTROL);
        write_stringz(out, container ? "containerSuspended" : "contextSuspended");

        json_write_string(out, ctx->id);
        write_stream(out, 0);

        write_context_state(out, ctx);

        if (container) {
            write_stream(out, '[');
            json_write_string(out, ctx->id);
            assert(!list_is_empty(&p1));
            while (!list_is_empty(&p1)) {
                LINK * m = p1.next;
                Context * x = link2ctx(m);
                list_remove(m);
                list_add_last(m, &p2);
                write_stream(out, ',');
                json_write_string(out, x->id);
            }
            write_stream(out, ']');
            write_stream(out, 0);
            assert(list_is_empty(&p1));
        }

        write_stream(out, MARKER_EOM);
    }

    l = p2.next;
    while (l != &p2) {
        Context * x = link2ctx(l);
        l = l->next;
        for (i = 0; i < listener_cnt; i++) {
            Listener * l = listeners + i;
            if (l->listener->context_intercepted == NULL) continue;
            l->listener->context_intercepted(x, l->args);
        }
        assert(x->pending_intercept == 0);
    }
}

static void send_event_context_resumed(Context * grp) {
    LINK * l = NULL;
    LINK p;

    list_init(&p);
    l = context_root.next;
    while (l != &context_root) {
        Context * ctx = ctxl2ctxp(l);
        ContextExtensionRC * ext = EXT(ctx);
        if (ext->intercepted && context_get_group(ctx, CONTEXT_GROUP_INTERCEPT) == grp) {
            assert(!ctx->pending_intercept);
            assert(!ext->safe_single_step);
            notify_context_released(ctx);
            list_add_last(&ext->link, &p);
        }
        l = l->next;
    }

    if (!list_is_empty(&p)) {
        OutputStream * out = &broadcast_group->out;

        write_stringz(out, "E");
        write_stringz(out, RUN_CONTROL);

        if (p.next == p.prev) {
            Context * ctx = link2ctx(p.next);
            write_stringz(out, "contextResumed");
            json_write_string(out, ctx->id);
        }
        else {
            l = p.next;
            write_stringz(out, "containerResumed");
            write_stream(out, '[');
            while (l != &p) {
                Context * ctx = link2ctx(l);
                if (l != p.next) write_stream(out, ',');
                json_write_string(out, ctx->id);
                l = l->next;
            }
            write_stream(out, ']');
        }
        write_stream(out, 0);

        write_stream(out, MARKER_EOM);
    }
}

static void send_event_context_exception(Context * ctx) {
    OutputStream * out = &broadcast_group->out;

    write_stringz(out, "E");
    write_stringz(out, RUN_CONTROL);
    write_stringz(out, "contextException");

    /* String: Context ID */
    json_write_string(out, ctx->id);
    write_stream(out, 0);

    /* String: Human readable description of the exception */
    if (ctx->exception_description) {
        json_write_string(out, ctx->exception_description);
    }
    else if (ctx->signal > 0) {
        char buf[128];
        const char * desc = signal_description(ctx->signal);
        if (desc == NULL) desc = signal_name(ctx->signal);
        snprintf(buf, sizeof(buf), desc == NULL ? "Signal %d" : "Signal %d: %s", ctx->signal, desc);
        json_write_string(out, buf);
    }
    else {
        json_write_string(out, context_suspend_reason(ctx));
    }
    write_stream(out, 0);

    write_stream(out, MARKER_EOM);
}

int is_all_stopped(Context * ctx) {
    LINK * l;
    Context * grp = context_get_group(ctx, CONTEXT_GROUP_STOP);
    for (l = context_root.next; l != &context_root; l = l->next) {
        Context * ctx = ctxl2ctxp(l);
        if (ctx->stopped || ctx->exited || ctx->exiting) continue;
        if (EXT(ctx)->cannot_stop) continue;
        if (!context_has_state(ctx)) continue;
        if (context_get_group(ctx, CONTEXT_GROUP_STOP) != grp) continue;
        return 0;
    }
    return 1;
}

int is_intercepted(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    return ext->intercepted;
}

#if EN_STEP_LINE

static int is_same_line(CodeArea * x, CodeArea * y) {
    if (x == NULL || y == NULL) return 0;
    if (x->start_line != y->start_line) return 0;
    if (x->directory != y->directory && (x->directory == NULL || strcmp(x->directory, y->directory))) return 0;
    if (x->file != y->file && (x->file == NULL || strcmp(x->file, y->file))) return 0;
    return 1;
}

static void update_step_machine_code_area(CodeArea * area, void * args) {
    ContextExtensionRC * ext = (ContextExtensionRC *)args;
    if (ext->step_code_area != NULL) return;
    ext->step_code_area = (CodeArea *)loc_alloc(sizeof(CodeArea));
    *ext->step_code_area = *area;
    if (area->directory != NULL) ext->step_code_area->directory = loc_strdup(area->directory);
    if (area->file != NULL) ext->step_code_area->file = loc_strdup(area->file);
}

static int is_function_prologue(Context * ctx, ContextAddress ip, CodeArea * area) {
#if ENABLE_Symbols
    Symbol * sym = NULL;
    int sym_class = SYM_CLASS_UNKNOWN;
    ContextAddress sym_addr = 0;
    ContextAddress sym_size = 0;
    assert(ip >= area->start_address && ip < area->end_address);
    if (find_symbol_by_addr(ctx, STACK_NO_FRAME, ip, &sym) < 0) return 0;
    if (get_symbol_class(sym, &sym_class) < 0) return 0;
    if (sym_class != SYM_CLASS_FUNCTION) return 0;
    if (get_symbol_size(sym, &sym_size) < 0) return 0;
    if (sym_size == 0) return 0;
    if (get_symbol_address(sym, &sym_addr) < 0) return 0;
    if (sym_addr >= area->start_address && sym_addr < area->end_address) return 1;
#endif
    return 0;
}

static int is_hidden_function(Context * ctx, ContextAddress ip,
        ContextAddress * addr0, ContextAddress * addr1) {
#if ENABLE_Symbols
    Symbol * sym = NULL;
    char * name = NULL;
    ContextAddress sym_addr = 0;
    ContextAddress sym_size = 0;
    if (find_symbol_by_addr(ctx, STACK_NO_FRAME, ip, &sym) < 0) return 0;
    if (get_symbol_name(sym, &name) < 0 || name == NULL) return 0;
    if (strcmp(name, "__i686.get_pc_thunk.bx") == 0) {
        if (get_symbol_address(sym, &sym_addr) < 0) return 0;
        if (get_symbol_size(sym, &sym_size) < 0 || sym_size == 0) {
            *addr0 = ip;
            *addr1 = ip + 1;
        }
        else {
            *addr0 = sym_addr;
            *addr1 = sym_addr + sym_size;
        }
        return 1;
    }
#endif
    return 0;
}

#if EN_STEP_OVER

static void get_machine_code_area(CodeArea * area, void * args) {
    *(CodeArea **)args = (CodeArea *)tmp_alloc(sizeof(CodeArea));
    memcpy(*(CodeArea **)args, area, sizeof(CodeArea));
}

static int is_within_function_epilogue(Context * ctx, ContextAddress ip) {
    Symbol * sym = NULL;
    int sym_class = SYM_CLASS_UNKNOWN;
    ContextAddress sym_addr = 0;
    ContextAddress sym_size = 0;
    CodeArea * area = NULL;
    if (find_symbol_by_addr(ctx, STACK_NO_FRAME, ip, &sym) < 0) return 0;
    if (get_symbol_class(sym, &sym_class) < 0) return 0;
    if (sym_class != SYM_CLASS_FUNCTION) return 0;
    if (get_symbol_size(sym, &sym_size) < 0) return 0;
    if (sym_size == 0) return 0;
    if (get_symbol_address(sym, &sym_addr) < 0) return 0;
    if (address_to_line(ctx, sym_addr + sym_size - 1, sym_addr + sym_size, get_machine_code_area, &area) < 0) return 0;
    if (area != NULL && ip > area->start_address && ip < area->end_address) return 1;
    return 0;
}

#endif /* EN_STEP_OVER */
#endif /* EN_STEP_LINE */

#if EN_STEP_OVER
static void step_machine_breakpoint(Context * ctx, void * args) {
}

static BreakpointInfo * create_step_machine_breakpoint(ContextAddress addr, Context * ctx) {
    static const char * attr_list[] = { BREAKPOINT_ENABLED, BREAKPOINT_LOCATION, BREAKPOINT_SERVICE };
    BreakpointAttribute * attrs = NULL;
    BreakpointAttribute ** ref = &attrs;
    char str[32];
    unsigned i;

    for (i = 0; i < sizeof(attr_list) / sizeof(char *); i++) {
        ByteArrayOutputStream buf;
        BreakpointAttribute * attr = (BreakpointAttribute *)loc_alloc_zero(sizeof(BreakpointAttribute));
        OutputStream * out = create_byte_array_output_stream(&buf);
        attr->name = loc_strdup(attr_list[i]);
        switch (i) {
        case 0:
            json_write_boolean(out, 1);
            break;
        case 1:
            snprintf(str, sizeof(str), "0x%" PRIX64, (uint64_t)addr);
            json_write_string(out, str);
            break;
        case 2:
            json_write_string(out, RUN_CONTROL);
            break;
        }
        write_stream(out, 0);
        get_byte_array_output_stream_data(&buf, &attr->value, NULL);
        *ref = attr;
        ref = &attr->next;
    }
    return create_eventpoint_ext(attrs, ctx, step_machine_breakpoint, NULL);
}
#endif

static int update_step_machine_state(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    ContextAddress addr = ext->pc;

    if (!context_has_state(ctx) || ctx->exited || ctx->pending_intercept) {
        cancel_step_mode(ctx);
        return 0;
    }

    if (ext->pc_error) {
        if (ctx->stopped && get_error_code(ext->pc_error) == ERR_NOT_ACTIVE) {
            switch (ext->step_mode) {
            case RM_STEP_OVER:
            case RM_STEP_INTO:
            case RM_STEP_OVER_LINE:
            case RM_STEP_INTO_LINE:
            case RM_STEP_OUT:
            case RM_STEP_OVER_RANGE:
            case RM_STEP_INTO_RANGE:
            case RM_UNTIL_ACTIVE:
                if (context_can_resume(ctx, ext->step_continue_mode = RM_UNTIL_ACTIVE)) return 0;
                break;
            case RM_REVERSE_STEP_OVER:
            case RM_REVERSE_STEP_INTO:
            case RM_REVERSE_STEP_OVER_LINE:
            case RM_REVERSE_STEP_INTO_LINE:
            case RM_REVERSE_STEP_OUT:
            case RM_REVERSE_STEP_OVER_RANGE:
            case RM_REVERSE_STEP_INTO_RANGE:
            case RM_REVERSE_UNTIL_ACTIVE:
                if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_UNTIL_ACTIVE)) return 0;
                break;
            }
        }
        errno = ext->pc_error;
        return -1;
    }

    assert(ctx->stopped);
    assert(ctx->pending_intercept == 0);
    assert(ext->intercepted == 0);

#if EN_STEP_OVER
    {
        ContextAddress step_bp_addr = 0;
        int do_reverse =
                ext->step_mode == RM_REVERSE_STEP_OVER ||
                ext->step_mode == RM_REVERSE_STEP_OVER_RANGE ||
                ext->step_mode == RM_REVERSE_STEP_OVER_LINE ||
                ext->step_mode == RM_REVERSE_STEP_OUT;

        switch (ext->step_mode) {
        case RM_STEP_OVER:
        case RM_STEP_OVER_RANGE:
        case RM_STEP_OVER_LINE:
        case RM_REVERSE_STEP_OVER:
        case RM_REVERSE_STEP_OVER_RANGE:
        case RM_REVERSE_STEP_OVER_LINE:
        case RM_SKIP_PROLOGUE:
            if (ext->step_cnt == 0) {
                StackFrame * info = NULL;
                if (get_frame_info(ctx, STACK_TOP_FRAME, &info) < 0) return -1;
                ext->step_inlined = info->inlined;
                ext->step_frame_fp = info->fp;
            }
            else if (addr < ext->step_range_start || addr >= ext->step_range_end) {
                StackFrame * info = NULL;
                int n = get_top_frame(ctx);
                if (n < 0) return -1;
                if (get_frame_info(ctx, n, &info) < 0) return -1;
                if (ext->step_frame_fp != info->fp) {
                    unsigned frame_cnt;
                    if (ext->step_bp_info != NULL) {
                        if (!do_reverse || ext->step_line_cnt > 1) {
                            ext->step_continue_mode = RM_RESUME;
                        }
                        else {
                            ext->step_continue_mode = RM_REVERSE_RESUME;
                        }
                        return 0;
                    }
                    if (do_reverse && is_within_function_epilogue(ctx, addr)) {
                        /* With some compilers, the stack walking code based on debug information does not work
                         * correctly if we are in the middle of the function epilogue. In this case, an invalid
                         * return address is provided but no error is raised. To avoid this issue, do not try to
                         * get the stack trace of a function while it is in the midle of the epilogue but instead
                         * skip the epilogue. This code is done only in reverse stepping mode because it is very
                         * unlikely to meet this condition while doing forward stepping.
                         */
                        ext->step_continue_mode = RM_REVERSE_STEP_INTO;
                        return 0;
                    }
                    for (frame_cnt = 0; frame_cnt < RC_STEP_MAX_STACK_FRAMES; frame_cnt++) {
                        n = get_prev_frame(ctx, n);
                        if (n < 0) {
                            if (get_error_code(errno) == ERR_CACHE_MISS) return -1;
                            break;
                        }
                        if (get_frame_info(ctx, n, &info) < 0) return -1;
                        if (ext->step_frame_fp == info->fp) {
                            uint64_t pc = 0;
                            if (read_reg_value(info, get_PC_definition(ctx), &pc) < 0) return -1;
                            step_bp_addr = (ContextAddress)pc;
                            break;
                        }
                    }
                }
                else if (ext->step_inlined < info->inlined) {
                    if (ext->step_bp_info != NULL) {
                        destroy_eventpoint(ext->step_bp_info);
                        ext->step_bp_info = NULL;
                    }
                    if (!do_reverse || ext->step_line_cnt > 1) {
                        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_OVER)) return 0;
                        ext->step_continue_mode = RM_STEP_INTO;
                    }
                    else {
                        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_OVER)) return 0;
                        ext->step_continue_mode = RM_REVERSE_STEP_INTO;
                    }
                    return 0;
                }
                else if (do_reverse) {
                    /* Workaround for GCC debug information that contains
                     * invalid stack frame information for function epilogues */
                    Symbol * sym_org = NULL;
                    Symbol * sym_now = NULL;
                    ContextAddress sym_org_addr = ext->step_range_start;
                    ContextAddress sym_now_addr = addr;
                    int anomaly =
                            find_symbol_by_addr(ctx, n, sym_now_addr, &sym_now) >= 0 &&
                            find_symbol_by_addr(ctx, n, sym_org_addr, &sym_org) >= 0 &&
                            get_symbol_address(sym_now, &sym_now_addr) >= 0 &&
                            get_symbol_address(sym_org, &sym_org_addr) >= 0 &&
                            sym_now_addr != sym_org_addr;
                    if (anomaly) {
                        /* Step over the anomaly */
                        ext->step_continue_mode = RM_REVERSE_STEP_INTO;
                        return 0;
                    }
                }
            }
            break;
        case RM_STEP_OUT:
        case RM_REVERSE_STEP_OUT:
            {
                StackFrame * info = NULL;
                int n = get_top_frame(ctx);
                if (n < 0) return -1;
                if (ext->step_cnt == 0) {
                    uint64_t ip = 0;
                    int p = get_prev_frame(ctx, n);
                    if (p < 0) {
                        set_errno(errno, "Cannot step out");
                        return -1;
                    }
                    if (get_frame_info(ctx, p, &info) < 0) return -1;
                    ext->step_inlined = info->inlined;
                    ext->step_frame_fp = info->fp;
                    if (info->area == NULL) {
                        if (read_reg_value(info, get_PC_definition(ctx), &ip) < 0) return -1;
                        step_bp_addr = (ContextAddress)ip;
                        break;
                    }
                }
                if (get_frame_info(ctx, n, &info) < 0) return -1;
                if (ext->step_frame_fp != info->fp) {
                    unsigned frame_cnt;
                    if (ext->step_bp_info != NULL) {
                        if (!do_reverse || ext->step_line_cnt > 1) {
                            ext->step_continue_mode = RM_RESUME;
                        }
                        else {
                            ext->step_continue_mode = RM_REVERSE_RESUME;
                        }
                        return 0;
                    }
                    for (frame_cnt = 0; frame_cnt < RC_STEP_MAX_STACK_FRAMES; frame_cnt++) {
                        n = get_prev_frame(ctx, n);
                        if (n < 0) {
                            if (get_error_code(errno) == ERR_CACHE_MISS) return -1;
                            break;
                        }
                        if (get_frame_info(ctx, n, &info) < 0) return -1;
                        if (ext->step_frame_fp == info->fp) {
                            uint64_t pc = 0;
                            if (read_reg_value(info, get_PC_definition(ctx), &pc) < 0) return -1;
                            step_bp_addr = (ContextAddress)pc;
                            break;
                        }
                    }
                }
                else if (ext->step_inlined < info->inlined) {
                    if (ext->step_bp_info != NULL) {
                        destroy_eventpoint(ext->step_bp_info);
                        ext->step_bp_info = NULL;
                    }
                    if (!do_reverse || ext->step_line_cnt > 1) {
                        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_OVER)) return 0;
                        ext->step_continue_mode = RM_STEP_INTO;
                    }
                    else {
                        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_OVER)) return 0;
                        ext->step_continue_mode = RM_REVERSE_STEP_INTO;
                    }
                    return 0;
                }
            }
            break;
        }

        if (step_bp_addr) {
            if (!do_reverse || ext->step_line_cnt > 1) {
                ext->step_continue_mode = RM_RESUME;
            }
            else {
                step_bp_addr--;
                ext->step_continue_mode = RM_REVERSE_RESUME;
            }
            if (ext->step_bp_info == NULL || ext->step_bp_addr != step_bp_addr) {
                if (ext->step_bp_info != NULL) destroy_eventpoint(ext->step_bp_info);
                ext->step_bp_info = create_step_machine_breakpoint(step_bp_addr, ctx);
                ext->step_bp_addr = step_bp_addr;
            }
            return 0;
        }

        if (ext->step_bp_info != NULL) {
            destroy_eventpoint(ext->step_bp_info);
            ext->step_bp_info = NULL;
        }
    }
#endif /* EN_STEP_OVER */

    switch (ext->step_mode) {
    case RM_RESUME:
    case RM_REVERSE_RESUME:
        {
            int mode = ext->step_mode;
            cancel_step_mode(ctx);
            ext->step_continue_mode = mode;
        }
        return 0;
    case RM_UNTIL_ACTIVE:
    case RM_REVERSE_UNTIL_ACTIVE:
        ctx->pending_intercept = 1;
        ext->step_done = REASON_ACTIVE;
        return 0;
    case RM_STEP_INTO:
    case RM_STEP_OVER:
    case RM_REVERSE_STEP_INTO:
    case RM_REVERSE_STEP_OVER:
        if (ext->step_cnt == 0) {
            ext->step_range_start = addr;
            ext->step_range_end = addr + 1;
        }
        /* fall through */
    case RM_STEP_INTO_RANGE:
    case RM_STEP_OVER_RANGE:
    case RM_REVERSE_STEP_INTO_RANGE:
    case RM_REVERSE_STEP_OVER_RANGE:
        if (ext->step_cnt > 0 && (addr < ext->step_range_start || addr >= ext->step_range_end)) {
            ctx->pending_intercept = 1;
            ext->step_done = REASON_STEP;
            return 0;
        }
        break;
#if EN_STEP_LINE
    case RM_STEP_INTO_LINE:
    case RM_STEP_OVER_LINE:
    case RM_REVERSE_STEP_INTO_LINE:
    case RM_REVERSE_STEP_OVER_LINE:
        if (ext->step_cnt == 0) {
            if (ext->step_mode == RM_STEP_INTO_LINE || ext->step_mode == RM_REVERSE_STEP_INTO_LINE) {
                StackFrame * info = NULL;
                if (get_frame_info(ctx, STACK_TOP_FRAME, &info) < 0) return -1;
                ext->step_chk_inline_frame = info->inlined || info->area;
                ext->step_inlined = info->inlined;
                ext->step_frame_fp = info->fp;
            }
            if (address_to_line(ctx, addr, addr + 1, update_step_machine_code_area, ext) < 0) return -1;
            if (ext->step_code_area != NULL) {
                ext->step_range_start = ext->step_code_area->start_address;
                ext->step_range_end = ext->step_code_area->end_address;
            }
            else {
                ext->step_range_start = addr;
                ext->step_range_end = addr + 1;
            }
        }
        else if (addr < ext->step_range_start || addr >= ext->step_range_end) {
            int same_line = 0;
            CodeArea * area = ext->step_code_area;
            if (area == NULL) {
                ctx->pending_intercept = 1;
                ext->step_done = REASON_STEP;
                return 0;
            }
            if (is_hidden_function(ctx, addr, &ext->step_range_start, &ext->step_range_end)) {
                /* Don't stop in a function that should be hidden during source level stepping */
                break;
            }
            ext->step_code_area = NULL;
            if (address_to_line(ctx, addr, addr + 1, update_step_machine_code_area, ext) < 0) {
                if (ext->step_code_area) free_code_area(ext->step_code_area);
                ext->step_code_area = area;
                return -1;
            }
            if (ext->step_code_area == NULL) {
                /* Line info not available for current IP */
#if ENABLE_Symbols
                if (is_plt_section(ctx, addr) != 0) {
                    /* Continue stepping to skip PLT entry */
                    ext->step_code_area = area;
                    ext->step_range_start = addr;
                    ext->step_range_end = addr + 1;
                    break;
                }
                else if (errno) {
                    ext->step_code_area = area;
                    return -1;
                }
#endif
                free_code_area(area);
                ctx->pending_intercept = 1;
                ext->step_done = REASON_STEP;
                return 0;
            }
            same_line = is_same_line(ext->step_code_area, area);
            free_code_area(area);

            /* We are doing reverse step-over/into line. The first line has already been skipped, we are now trying to reach
             * the beginning of previous line. If we are still on same line but have reached the beginning of the line, then we
             * are done.
             */
            if (same_line &&
                    (ext->step_mode == RM_REVERSE_STEP_INTO_LINE || ext->step_mode == RM_REVERSE_STEP_OVER_LINE) &&
                    ext->step_line_cnt > 0 && addr == ext->step_code_area->start_address) {
                ctx->pending_intercept = 1;
                ext->step_done = REASON_STEP;
                return 0;
            }
            if (!same_line && !is_function_prologue(ctx, addr, ext->step_code_area)) {
                if ((ext->step_mode != RM_REVERSE_STEP_INTO_LINE && ext->step_mode != RM_REVERSE_STEP_OVER_LINE) ||
                        (ext->step_line_cnt == 0 && addr == ext->step_code_area->start_address) ||
                        ext->step_line_cnt >= 2) {
                    ctx->pending_intercept = 1;
                    ext->step_done = REASON_STEP;
                    return 0;
                }
                /* Current IP is in the middle of a source line.
                 * Continue stepping to get to the beginning of the line */
                ext->step_line_cnt++;
            }
            ext->step_range_start = ext->step_code_area->start_address;
            ext->step_range_end = ext->step_code_area->end_address;

            /* When doing reverse step-into/over line, if we have already skipped the first line, we want to reach
             * the beginning of current line, fix step range to handle this.
             */
            if ((ext->step_mode == RM_REVERSE_STEP_INTO_LINE || ext->step_mode == RM_REVERSE_STEP_OVER_LINE) &&
                    ext->step_line_cnt > 0) {
                ext->step_range_start += 1;
            }
        }
        else if (ext->step_chk_inline_frame) {
            StackFrame * info = NULL;
            if (get_frame_info(ctx, STACK_TOP_FRAME, &info) < 0) return -1;
            if (ext->step_inlined != info->inlined || ext->step_frame_fp != info->fp) {
                ctx->pending_intercept = 1;
                ext->step_done = REASON_STEP;
                return 0;
            }
        }
        break;
#if EN_STEP_OVER
    case RM_SKIP_PROLOGUE:
        {
            CodeArea * area = NULL;
            if (address_to_line(ctx, addr, addr + 1, get_machine_code_area, &area) < 0) return 0;
            if (area == NULL || !is_function_prologue(ctx, addr, area)) {
                ctx->pending_intercept = 1;
                ext->step_done = REASON_STEP;
                return 0;
            }
        }
        break;
#endif /* EN_STEP_OVER */
#endif /* EN_STEP_LINE */
    case RM_STEP_OUT:
    case RM_REVERSE_STEP_OUT:
        ctx->pending_intercept = 1;
        ext->step_done = REASON_STEP;
        return 0;
    default:
        errno = ERR_UNSUPPORTED;
        return -1;
    }

    if (ext->step_line_cnt > 1) {
        if (ext->step_mode == RM_REVERSE_STEP_INTO_LINE) ext->step_continue_mode = RM_STEP_INTO_LINE;
        if (ext->step_mode == RM_REVERSE_STEP_OVER_LINE) ext->step_continue_mode = RM_STEP_OVER_LINE;
    }
    else {
        ext->step_continue_mode = ext->step_mode;
        if (ext->step_line_cnt == 0 && context_can_resume(ctx, ext->step_continue_mode)) return 0;
    }

    switch (ext->step_continue_mode) {
    case RM_STEP_INTO_LINE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_INTO_RANGE)) return 0;
        break;
    case RM_STEP_OVER_LINE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_OVER_RANGE)) return 0;
        break;
    case RM_REVERSE_STEP_INTO_LINE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_INTO_RANGE)) return 0;
        break;
    case RM_REVERSE_STEP_OVER_LINE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_OVER_RANGE)) return 0;
        break;
    }

    switch (ext->step_continue_mode) {
    case RM_STEP_OVER:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_INTO)) return 0;
        break;
    case RM_STEP_OVER_RANGE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_INTO_RANGE)) return 0;
        break;
    case RM_REVERSE_STEP_OVER:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_INTO)) return 0;
        break;
    case RM_REVERSE_STEP_OVER_RANGE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_INTO_RANGE)) return 0;
        break;
    case RM_SKIP_PROLOGUE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_INTO)) return 0;
        break;
    }

    switch (ext->step_continue_mode) {
    case RM_STEP_INTO_RANGE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_STEP_INTO)) return 0;
        break;
    case RM_REVERSE_STEP_INTO_RANGE:
        if (context_can_resume(ctx, ext->step_continue_mode = RM_REVERSE_STEP_INTO)) return 0;
        break;
    }

    errno = ERR_UNSUPPORTED;
    return -1;
}

static void stop_all_timer(void * args) {
    stop_all_timer_posted = 0;
    stop_all_timer_cnt++;
    run_safe_events_posted++;
    post_event(run_safe_events, NULL);
}

static void resume_error(Context * ctx, int error) {
    ContextExtensionRC * ext = EXT(ctx);
    trace(LOG_ALWAYS, "Cannot resume context %s: %s", ctx->id, errno_to_str(error));
    if (context_has_state(ctx)) {
        error = set_errno(error, ext->step_bp_info ? "Cannot continue stepping" : "Cannot resume");
        ctx->signal = 0;
        ctx->stopped = 1;
        ctx->stopped_by_bp = 0;
        ctx->stopped_by_cb = NULL;
        ctx->stopped_by_exception = 1;
        ctx->pending_intercept = 1;
        loc_free(ctx->exception_description);
        ctx->exception_description = loc_strdup(errno_to_str(error));
        send_context_changed_event(ctx);
    }
}

static void check_step_breakpoint_instances(InputStream * inp, void * args);

static void check_step_breakpoint_status(InputStream * inp, const char * name, void * args) {
    if (strcmp(name, "Error") == 0) {
        char * msg = json_read_alloc_string(inp);
        if (msg != NULL) {
            *(int *)args = set_errno(ERR_OTHER, msg);
            loc_free(msg);
        }
    }
    else if (strcmp(name, "Instances") == 0) {
        json_read_array(inp, check_step_breakpoint_instances, args);
    }
    else {
        json_skip_object(inp);
    }
}

static void check_step_breakpoint_instances(InputStream * inp, void * args) {
    json_read_struct(inp, check_step_breakpoint_status, args);
}

static int check_step_breakpoint(Context * ctx) {
    /* Return error if step machine breakpoint cannot be planted */
    int error = 0;
    char * status = NULL;
    ByteArrayInputStream buf;
    InputStream * inp = NULL;
    ContextExtensionRC * ext = EXT(ctx);
    if (ext->step_bp_info == NULL) return 0;
    status = get_breakpoint_status(ext->step_bp_info);
    inp = create_byte_array_input_stream(&buf, status, strlen(status));
    json_read_struct(inp, check_step_breakpoint_status, &error);
    loc_free(status);
    if (!error) return 0;
    errno = error;
    return -1;
}

#if EN_STEP_OVER
static Channel * select_skip_prologue_channel(void) {
    /* TODO: better logic to select symbols server channel for skipping function prologue */
    Channel * def = NULL;
    LINK * l = channel_root.next;
    while (l != &channel_root) {
        Channel * c = chanlink2channelp(l);
        if (!is_channel_closed(c)) {
            int i;
            for (i = 0; i < c->peer_service_cnt; i++) {
                char * nm = c->peer_service_list[i];
                if (strcmp(nm, "Symbols") == 0) return c;
            }
            def = c;
        }
        l = l->next;
    }
    return def;
}
#endif

static void sync_run_state(void) {
    int err_cnt = 0;
    LINK * l;
    LINK p;

    if (run_ctrl_lock_cnt != 0) return;
    assert(safe_event_list == NULL);
    stop_all_timer_cnt = 0;

    /* Clear intercept group flags, get current PCs */
    safe_event_pid_count = 0;
    l = context_root.next;
    while (l != &context_root) {
        Context * ctx = ctxl2ctxp(l);
        ContextExtensionRC * ext = EXT(ctx);
        l = l->next;
        ext->pc = 0;
        ext->pc_error = ERR_OTHER;
        ext->pending_safe_event = 0;
        if (context_has_state(ctx)) {
            Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
            if (!ctx->exited && ctx->stopped && !ext->intercepted) get_current_pc(ctx);
            EXT(grp)->intercept_group = 0;
        }
        else if (ext->step_mode == RM_TERMINATE || ext->step_mode == RM_DETACH) {
            int md = ext->step_mode;
            assert(is_all_stopped(ctx));
            if (context_resume(ctx, md, 0, 0) < 0) {
                if (cache_miss_count() > 0) return;
                resume_error(ctx, errno);
            }
            ext->step_mode = RM_RESUME;
        }
    }

    /* Set intercept group flags */
    l = context_root.next;
    while (l != &context_root) {
        Context * ctx = ctxl2ctxp(l);
        ContextExtensionRC * ext = EXT(ctx);
        l = l->next;
        if (ctx->exited) continue;
        if (ctx->pending_intercept || ext->intercepted) {
            Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
            EXT(grp)->intercept_group = 1;
            continue;
        }
        if (!ctx->stopped) continue;
        if (ext->step_mode == RM_RESUME && ext->skip_prologue) {
#if EN_STEP_OVER
            start_step_mode(ctx, select_skip_prologue_channel(), RM_SKIP_PROLOGUE, 0, 0);
#else
            Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
            EXT(grp)->intercept_group = 1;
            continue;
#endif
        }
        if (ext->step_mode == RM_RESUME || ext->step_mode == RM_REVERSE_RESUME ||
            ext->step_mode == RM_TERMINATE || ext->step_mode == RM_DETACH) {
                ext->step_continue_mode = ext->step_mode;
        }
        else if (ext->step_channel != NULL && is_channel_closed(ext->step_channel)) {
            cancel_step_mode(ctx);
        }
        else {
            cache_set_def_channel(ext->step_channel);
            if (update_step_machine_state(ctx) < 0) {
                int error = errno;
                Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
                if (cache_miss_count() > 0) return;
                release_error_report(ext->step_error);
                ext->step_error = get_error_report(error);
                cancel_step_mode(ctx);
                EXT(grp)->intercept_group = 1;
            }
            else if (ctx->pending_intercept) {
                Context * grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
                EXT(grp)->intercept_group = 1;
            }
            cache_set_def_channel(NULL);
        }
    }

    /* Stop or continue contexts as needed */
    list_init(&p);
    l = context_root.next;
    while (err_cnt == 0 && run_ctrl_lock_cnt == 0 && l != &context_root) {
        Context * grp = NULL;
        Context * ctx = ctxl2ctxp(l);
        ContextExtensionRC * ext = EXT(ctx);
        l = l->next;
        if (ctx->exited) continue;
        if (ext->intercepted) continue;
        if (!context_has_state(ctx)) continue;
        grp = context_get_group(ctx, CONTEXT_GROUP_INTERCEPT);
        if (EXT(grp)->intercept_group) {
            ctx->pending_intercept = 1;
            if (!ctx->stopped && !ctx->exiting) {
                assert(!ext->safe_single_step);
                context_stop(ctx);
                ext->pending_safe_event = 1;
                safe_event_pid_count++;
                assert(!ctx->stopped);
            }
        }
        else if (ctx->stopped && !ctx->pending_intercept && ext->run_ctrl_ctx_lock_cnt == 0) {
            if (check_step_breakpoint(ctx) < 0) {
                if (cache_miss_count() > 0) return;
                resume_error(ctx, errno);
                err_cnt++;
            }
            else if (ext->step_continue_mode != RM_RESUME) {
                list_add_last(&ext->link, &p);
            }
            else if (context_resume(ctx, EXT(grp)->reverse_run ? RM_REVERSE_RESUME : RM_RESUME, 0, 0) < 0) {
                if (cache_miss_count() > 0) return;
                resume_error(ctx, errno);
                err_cnt++;
            }
        }
    }

    /* Resume contexts with resume mode other then RM_RESUME */
    l = p.next;
    while (err_cnt == 0 && run_ctrl_lock_cnt == 0 && l != &p) {
        int error = 0;
        Context * ctx = link2ctx(l);
        ContextExtensionRC * ext = EXT(ctx);
        assert(!ext->intercepted);
        l = l->next;
        if (ext->step_continue_mode == RM_STEP_INTO) {
            int done = 0;
            if (step_into_inlined_frame(ctx, &done) < 0) error = errno;
            if (!error && done) {
                ext->step_cnt++;
                if (run_safe_events_posted < 4) {
                    run_safe_events_posted++;
                    post_event(run_safe_events, NULL);
                }
                continue;
            }
        }
        if (!error && context_resume(ctx, ext->step_continue_mode, ext->step_range_start, ext->step_range_end) < 0) error = errno;
        if (error) {
            if (cache_miss_count() > 0) return;
            resume_error(ctx, error);
            err_cnt++;
        }
    }

    if (safe_event_pid_count > 0 || run_ctrl_lock_cnt > 0) return;

    if (err_cnt > 0 && run_safe_events_posted < 4) {
        run_safe_events_posted++;
        post_event(run_safe_events, NULL);
    }
}

static void sync_run_state_cache_client(void * args) {
    sync_run_state();
    cache_exit();
    if (run_safe_events_posted || run_ctrl_lock_cnt > 0) return;
    send_event_context_suspended();
}

static void sync_run_state_event(void * args) {
    cache_enter(sync_run_state_cache_client, NULL, NULL, 0);
}

static void mark_stop_groups(void) {
    LINK * l = context_root.next;
    SafeEvent * e = safe_event_list;
    while (l != &context_root) {
        Context * grp = context_get_group(ctxl2ctxp(l), CONTEXT_GROUP_STOP);
        EXT(grp)->stop_group_mark = 0;
        l = l->next;
    }
    while (e != NULL) {
        Context * grp = context_get_group(e->ctx, CONTEXT_GROUP_STOP);
        EXT(grp)->stop_group_mark = 1;
        e = e->next;
    }
}

static void run_safe_events(void * arg) {
    LINK * l;

    run_safe_events_posted--;
    if (run_safe_events_posted > 0) return;

    if (run_ctrl_lock_cnt == 0) {
        post_event(sync_run_state_event, NULL);
        return;
    }

    if (safe_event_list == NULL) return;

    mark_stop_groups();
    safe_event_pid_count = 0;

    l = context_root.next;
    while (l != &context_root) {
        Context * ctx = ctxl2ctxp(l);
        ContextExtensionRC * ext = EXT(ctx);
        l = l->next;
        ext->pending_safe_event = 0;
        if (ctx->exited || ctx->exiting || ext->cannot_stop) continue;
        if (ctx->stopped || !context_has_state(ctx)) continue;
        if (!ext->safe_single_step && !EXT(context_get_group(ctx, CONTEXT_GROUP_STOP))->stop_group_mark) continue;
        if (stop_all_timer_cnt >= STOP_ALL_MAX_CNT) {
            trace(LOG_ALWAYS, "can't stop %s: timeout", ctx->id);
            ext->cannot_stop = 1;
            continue;
        }
        if (stop_all_timer_cnt >= 2 && ext->state_name != NULL) {
            trace(LOG_ALWAYS, "can't stop %s: %s", ctx->id, ext->state_name);
            ext->cannot_stop = 1;
            continue;
        }
#if ENABLE_Trace
        if (stop_all_timer_cnt == STOP_ALL_MAX_CNT / 2) {
            const char * msg = ext->safe_single_step ? "finish single step" : "stop";
            trace(LOG_ALWAYS, "warning: waiting too long for context %s to %s", ctx->id, msg);
        }
#endif
        if (!ext->safe_single_step || stop_all_timer_cnt >= STOP_ALL_MAX_CNT / 2) {
            if (context_stop(ctx) < 0) {
                trace(LOG_ALWAYS, "can't stop %s: %s", ctx->id, errno_to_str(errno));
                ext->cannot_stop = 1;
                continue;
            }
            assert(!ctx->stopped);
        }
        ext->pending_safe_event = 1;
        safe_event_pid_count++;
    }

    if (safe_event_pid_count == 0) {
        stop_all_timer_cnt = 0;
        if (stop_all_timer_posted) {
            cancel_event(stop_all_timer, NULL, 0);
            stop_all_timer_posted = 0;
        }
    }

    while (safe_event_list) {
        Trap trap;
        SafeEvent * i = safe_event_list;
        if (!EXT(context_get_group(i->ctx, CONTEXT_GROUP_STOP))->stop_group_mark) {
            assert(run_ctrl_lock_cnt > 0);
            if (run_safe_events_posted == 0) {
                run_safe_events_posted++;
                post_event(run_safe_events, NULL);
            }
            break;
        }
        if (safe_event_pid_count > 0) {
            if (!stop_all_timer_posted) {
                stop_all_timer_posted = 1;
                post_event_with_delay(stop_all_timer, NULL, STOP_ALL_TIMEOUT);
            }
            break;
        }
        assert(is_all_stopped(i->ctx));
        safe_event_list = i->next;
        if (safe_event_list == NULL) safe_event_last = NULL;
        if (i->done != NULL) {
            safe_event_active = 1;
            if (set_trap(&trap)) {
                i->done(i->arg);
                clear_trap(&trap);
            }
            else {
                trace(LOG_ALWAYS, "Unhandled exception in \"safe\" event dispatch: %d %s",
                      trap.error, errno_to_str(trap.error));
            }
            safe_event_active = 0;
        }
        run_ctrl_unlock();
        context_unlock(i->ctx);
        loc_free(i);
    }
    if (safe_event_list == NULL) cache_notify(&safe_events_cache);
}

static void check_safe_events(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    assert(ctx->stopped || ctx->exited);
    assert(ext->pending_safe_event);
    assert(safe_event_pid_count > 0);
    ext->pending_safe_event = 0;
    safe_event_pid_count--;
    if (safe_event_pid_count == 0) {
        run_safe_events_posted++;
        post_event(run_safe_events, NULL);
    }
}

void post_safe_event(Context * ctx, EventCallBack * done, void * arg) {
    SafeEvent * i = (SafeEvent *)loc_alloc_zero(sizeof(SafeEvent));
    run_ctrl_lock();
    context_lock(ctx);
    if (safe_event_list == NULL) {
        run_safe_events_posted++;
        post_event(run_safe_events, NULL);
    }
    /* Note: context stop group can change
     * while the event is waiting in the queue */
    i->ctx = ctx;
    i->done = done;
    i->arg = arg;
    if (safe_event_list == NULL) safe_event_list = i;
    else safe_event_last->next = i;
    safe_event_last = i;
}

int is_safe_event(void) {
    return safe_event_active;
}

void check_all_stopped(Context * ctx) {
    if (is_all_stopped(ctx)) return;
    post_safe_event(ctx, NULL, NULL);
    cache_wait(&safe_events_cache);
}

int safe_context_single_step(Context * ctx) {
    int res = 0;
    ContextExtensionRC * ext = EXT(ctx);
    assert(run_ctrl_lock_cnt > 0);
    assert(safe_event_list != NULL);
    assert(ext->safe_single_step == 0);
    ext->safe_single_step = 1;
    res = context_resume(ctx, RM_STEP_INTO, 0, 0);
    assert(res < 0 || !ctx->stopped);
    if (res < 0) ext->safe_single_step = 0;
    return res;
}

void run_ctrl_lock(void) {
    if (run_ctrl_lock_cnt == 0) {
        assert(safe_event_list == NULL);
#if ENABLE_Cmdline
        cmdline_suspend();
#endif
    }
    run_ctrl_lock_cnt++;
}

void run_ctrl_unlock(void) {
    assert(run_ctrl_lock_cnt > 0);
    run_ctrl_lock_cnt--;
    if (run_ctrl_lock_cnt == 0) {
        assert(safe_event_list == NULL);
#if ENABLE_Cmdline
        cmdline_resume();
#endif
        /* Lazily continue execution of temporary stopped contexts */
        run_safe_events_posted++;
        post_event(run_safe_events, NULL);
    }
}

void run_ctrl_ctx_lock(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    assert(context_has_state(ctx));
    ext->run_ctrl_ctx_lock_cnt++;
}

void run_ctrl_ctx_unlock(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    assert(context_has_state(ctx));
    assert(ext->run_ctrl_ctx_lock_cnt > 0);
    ext->run_ctrl_ctx_lock_cnt--;
    if (ext->run_ctrl_ctx_lock_cnt == 0) {
        /* Lazily continue execution of temporary stopped contexts */
        run_safe_events_posted++;
        post_event(run_safe_events, NULL);
    }
}

void set_context_state_name(Context * ctx, const char * name) {
    ContextExtensionRC * ext = EXT(ctx);
    OutputStream * out = &broadcast_group->out;

    if (name != NULL) {
        if (ext->state_name != NULL) {
            if (strcmp(ext->state_name, name) == 0) return;
            loc_free(ext->state_name);
        }
        ext->state_name = loc_strdup(name);
    }
    else {
        if (ext->state_name == NULL) return;
        loc_free(ext->state_name);
        ext->state_name = NULL;
    }

    if (!ext->intercepted) {
        write_stringz(out, "E");
        write_stringz(out, RUN_CONTROL);
        write_stringz(out, "contextStateChanged");

        json_write_string(out, ctx->id);
        write_stream(out, 0);

        write_stream(out, MARKER_EOM);
    }
}

void add_run_control_event_listener(RunControlEventListener * listener, void * args) {
    if (listener_cnt >= listener_max) {
        listener_max += 8;
        listeners = (Listener *)loc_realloc(listeners, listener_max * sizeof(Listener));
    }
    listeners[listener_cnt].listener = listener;
    listeners[listener_cnt].args = args;
    listener_cnt++;
}

void rem_run_control_event_listener(RunControlEventListener * listener) {
    unsigned i = 0;
    while (i < listener_cnt) {
        if (listeners[i++].listener == listener) {
            while (i < listener_cnt) {
                listeners[i - 1] = listeners[i];
                i++;
            }
            listener_cnt--;
            break;
        }
    }
}

static void stop_if_safe_events(Context * ctx) {
    ContextExtensionRC * ext = EXT(ctx);
    assert(run_ctrl_lock_cnt == 0 || !ext->safe_single_step || safe_event_list != NULL);
    if (run_ctrl_lock_cnt && !ctx->exiting && !ctx->stopped && context_has_state(ctx)) {
        if (!ext->safe_single_step) {
            context_stop(ctx);
        }
        if (!ext->pending_safe_event) {
            ext->pending_safe_event = 1;
            safe_event_pid_count++;
        }
    }
}

static void event_context_created(Context * ctx, void * args) {
    assert(!ctx->exited);
    assert(!ctx->stopped);
    send_event_context_added(ctx);
    stop_if_safe_events(ctx);
}

static void event_context_changed(Context * ctx, void * args) {
    assert(!ctx->exited);
    send_event_context_changed(ctx);
    stop_if_safe_events(ctx);
}

static void event_context_stopped(Context * ctx, void * args) {
    ContextExtensionRC * ext = EXT(ctx);
    assert(ctx->stopped);
    assert(!ctx->exited);
    assert(!ext->intercepted);
    ext->safe_single_step = 0;
    ext->cannot_stop = 0;
    if (ext->step_mode) {
        ext->step_cnt++;
    }
    else {
        if (ext->step_error != NULL) {
            release_error_report(ext->step_error);
            ext->step_error = NULL;
        }
        ext->step_done = NULL;
    }
#if SERVICE_Breakpoints
    if (ctx->stopped_by_bp || ctx->stopped_by_cb) evaluate_breakpoint(ctx);
#endif
    if (ext->pending_safe_event) check_safe_events(ctx);
    if (ctx->stopped_by_exception) send_event_context_exception(ctx);
    if (run_ctrl_lock_cnt == 0 && run_safe_events_posted < 4) {
        /* Lazily continue execution of temporary stopped contexts */
        run_safe_events_posted++;
        post_event(run_safe_events, NULL);
    }
}

static void event_context_started(Context * ctx, void * args) {
    ContextExtensionRC * ext = EXT(ctx);
    assert(!ctx->stopped);
    assert(!ctx->exited);
    if (ext->intercepted) resume_context_tree(ctx);
    stop_if_safe_events(ctx);
}

static void event_context_exited(Context * ctx, void * args) {
    ContextExtensionRC * ext = EXT(ctx);
    ext->safe_single_step = 0;
    cancel_step_mode(ctx);
    send_event_context_removed(ctx);
    if (ext->pending_safe_event) check_safe_events(ctx);
}

static void channel_closed(Channel * c) {
    LINK * l;
    for (l = context_root.next; l != &context_root; l = l ->next) {
        Context * ctx = ctxl2ctxp(l);
        ContextExtensionRC * ext = EXT(ctx);
        if (ext->step_channel == c) cancel_step_mode(ctx);
    }
}

static void event_context_disposed(Context * ctx, void * args) {
    ContextExtensionRC * ext = EXT(ctx);
    cancel_step_mode(ctx);
    if (ext->step_error) {
        release_error_report(ext->step_error);
        ext->step_error = NULL;
    }
    loc_free(ext->state_name);
    while (ext->bp_cnt > 0) loc_free(ext->bp_ids[--ext->bp_cnt]);
    loc_free(ext->bp_ids);
}

static int cmp_has_state(Context * ctx, const char * v) {
    int x = strcmp(v, "true") == 0 || strcmp(v, "1") == 0;
    int y = context_has_state(ctx) != 0;
    return x == y;
}

static int cmp_parent_id(Context * ctx, const char * v) {
    return ctx->parent != NULL && strcmp(ctx->parent->id, v) == 0;
}

static int cmp_creator_id(Context * ctx, const char * v) {
    return ctx->creator != NULL && strcmp(ctx->creator->id, v) == 0;
}

static int cmp_process_id(Context * ctx, const char * v) {
    ctx = context_get_group(ctx, CONTEXT_GROUP_PROCESS);
    return ctx != NULL && strcmp(ctx->id, v) == 0;
}

void ini_run_ctrl_service(Protocol * proto, TCFBroadcastGroup * bcg) {
    static ContextEventListener listener = {
        event_context_created,
        event_context_exited,
        event_context_stopped,
        event_context_started,
        event_context_changed,
        event_context_disposed
    };
    broadcast_group = bcg;
    add_context_event_listener(&listener, NULL);
    add_channel_close_listener(channel_closed);
    context_extension_offset = context_extension(sizeof(ContextExtensionRC));
    add_command_handler(proto, RUN_CONTROL, "getContext", command_get_context);
    add_command_handler(proto, RUN_CONTROL, "getChildren", command_get_children);
    add_command_handler(proto, RUN_CONTROL, "getState", command_get_state);
#if ENABLE_ContextISA
    add_command_handler(proto, RUN_CONTROL, "getISA", command_get_isa);
#endif
    add_command_handler(proto, RUN_CONTROL, "resume", command_resume);
    add_command_handler(proto, RUN_CONTROL, "suspend", command_suspend);
    add_command_handler(proto, RUN_CONTROL, "terminate", command_terminate);
    add_command_handler(proto, RUN_CONTROL, "detach", command_detach);
    add_context_query_comparator("HasState", cmp_has_state);
    add_context_query_comparator("ParentID", cmp_parent_id);
    add_context_query_comparator("CreatorID", cmp_creator_id);
    add_context_query_comparator("ProcessID", cmp_process_id);
}

#endif /* SERVICE_RunControl */
