erlang如何使用一个OS线程实现抢占式调度?

时间:2018-03-03 01:10:13

标签: erlang scheduling preemptive green-threads

我想知道erlang的VM如何抢占正在运行的代码并使用栈上下文。如何用c?

这样的语言来完成

2 个答案:

答案 0 :(得分:2)

诀窍是Erlang运行时可以控制VM,因此它可以-完全在用户空间中-跟踪已经执行了多少VM指令(或者更好的是估计或表示所需的实际物理计算)对于这些指令-在Erlang VM中也称为“减少”),并且-如果该数目超过某个阈值,则立即在进程指针/结构/所有内容之间交换并恢复执行循环。

想到这样的东西(某种可能是或可能不是C的伪C,但我不知道是因为我不是C程序员,但是您问过要怎么做)它以C语言显示,因此我将尽我所能):

void proc_execute(Proc* proc)
{
    /* I don't recall if Erlang's VM supports different
       reduction limits for different processes, but if it
       did, it'd be a rather intuitive way to define process
       priorities, i.e. making sure higher-priority processes
       get more reductions to spend */
    int rds = proc->max_reductions;

    for (; rds > 0; rds--) {
        /* Different virtual instructions might execute different numbers of
           physical instructions, so vm_execute_next_instruction will return
           however many reductions are left after executing that virtual
           instruction. */
        rds = vm_execute_next_instruction(proc, rds);
        if (proc->exited) break;
    }
}

void vm_loop(Scheduler* sched)
{
    Proc *proc;

    for (;;) {
        proc = sched_next_in_queue(sched);
        /* we'll assume that the proc will be null if the
           scheduler doesn't have any processes left in its
           list */
        if (!proc) break;
        proc_execute(proc);
    }
}

Proc* sched_next_in_queue(Scheduler* sched)
{
    if (!sched->current_proc->exited) {
        /* If the process hasn't exited yet, readd it to the
           end of the queue so we can resume running it
           later */
        shift(sched->queue, sched->current_proc);
    }
    sched->current_proc = pop(sched->queue);
    return sched->current_proc;
}

这显然是相当简化的(特别是排除/消除了许多重要的东西,例如如何实现VM指令以及如何传递消息),但是希望它可以说明(至少在我理解正确的情况下)Erlang的抢先式调度程序和过程模型在基本级别上起作用。

答案 1 :(得分:0)

Erlang的所有代码都将编译为Erlang VM的操作代码。 Erlang的VM通过在Erlang的VM启动时创建的OS线程执行Erlang的操作代码。

Erlang的代码在由Erlang的VM控制的虚拟CPU上运行。 Erlang的VM将IO视为虚拟CPU的中断。因此,Erlang的VM实现了一台机器和一个像操作系统一样的调度程序。由于操作代码和非阻塞IO,我们可以使用C语言在Erlang的VM中实现抢占。