Lua中的多线程

RCI*_*CIX 9 lua multithreading preemptive

前几天我和朋友讨论过.我说的是,在纯粹的Lua中,你无法建立一个抢先式的多任务系统.他声称你可以,因为以下原因:

C和Lua都没有内置的线程库[OP的注释:嗯,Lua技术上确实如此,但AFAIK对我们的目的没用].Windows,主要是用C(++)编写的,具有先发制人的多任务处理,它们是从头开始构建的.因此,你应该能够在Lua中做同样的事情.我看到的一个大问题是抢先式多任务工作的主要方式(据我所知)是它产生定期中断,经理用它来控制并确定下一步应该处理的代码.我也不认为Lua有任何设施可以做到这一点.

我的问题是:是否有可能编写一个纯Lua库,允许人们进行先发制人的多任务处理?

Nor*_*sey 9

我看不出怎么做,虽然没有Lua的正式语义(例如语义yield),但很难想出一个为什么不能做到的铁定论证.(我一直在想一个正式的语义的年龄,但显然罗伯托和LHF有更好的事情要做.)

如果我想为Lua进行先发制人的多任务处理,我甚至不会尝试在纯Lua中进行.相反,我会使用我20年前在新泽西州标准ML中首次看到的旧技巧:

  • 中断在lua_State"当前协程已被抢占" 的说法中设置了一个标志.

  • 更改VM,以便在每个循环和每个函数调用时,它会检查标志并在必要时生成.

这个补丁很容易编写,易于维护.它并没有解决长期运行的C函数无法预先解决的问题,但是如果你必须解决这个问题,你就会徘徊在更加困难的领域,你也可以做所有的线程处理C级,而不是Lua级.


Twi*_*sol 5

不是我知道的,不.如果你可以通过debug.sethook从协同程序设置的钩子中产生几乎是荒谬的,但它不起作用.你可以从C(lua_sethook)设置的C钩子中得到,但我无法弄清楚到底是什么,而且它不是纯粹的Lua.

即使有可能,也不会是真正的线程.例如,一切仍将在同一操作系统线程中运行.您的钩子会考虑各种因素(例如时间,可能是记忆等),然后确定是否屈服.然后屈服于协同程序将决定下一个运行哪个子协程.您还需要决定何时应该调用钩子.最常见的是每个Lua指令,但这会带来性能损失.如果协程调用C函数,Lua没有管辖权.如果那个C调用需要很长时间,那么你无能为力.

是Lua-L邮件列表中的一个相关主题,您可能会感兴趣.


Jef*_*per 5

不可以.在纯Lua中编写抢占式调度程序是不可能的.在某些时候,抢占式调度程序需要一些机制,如中断服务程序,以控制远离当前线程并将其提供给调度程序,然后调度程序可以将其提供给另一个线程.Pure Lua没有这种机制.

你提到Windows主要是用C/C++编写的.关键字主要是.您无法在纯ANSI C/C++中编写抢占式调度程序.通常,部分中断服务程序是用汇编语言编写的.或者,C/C++编译器实现了一个非标准扩展,允许用C/C++编写中断服务程序.有些编译器允许您使用__interrupt修饰符声明一个函数,该函数会导致编译器生成一个延长/ epilog,允许该函数用作中断服务例程.

此外,设置中断服务程序的代码会对带有内存映射IO的CPU寄存器或IO指令进行调整.这些代码都不是可移植的ANSI C/C++.而且,取决于CPU架构.