Ameba , 一个简单的 lua 多线程实现
几个月以前,在我在 blog 上曾谈及 Lua 5.2 的改进。它可以用来实现抢占式多线程 。
周末休息,我把这桩事挖出来娱乐一下,花了一整个晚上做了实现。把 lua 的每个线程锁定在独立的 lua state 中,强迫线程之间通过消息管道的方式通讯。经过测试,Lua 5.2 每个独立的 state 占用的内存很小。通过自定义 alloc 函数可以测算出,一个干净的 32bit state ,不含任何库函数时,占用内存量在 2K 以下(1726 bytes)。如果加载基本库,也仅仅占用不到 4K (3265 bytes)。若把所有 lua 官方标准库加载进来,才会上升到 10K 以上(12456 bytes)。
对于 luajit 2 ,这个基础开销会大一些,最小开销也在 10K 左右 (8058 bytes) 。加上 ffi 达到 30k (31605 bytes)。不过 ffi 可以使 lua 代码直接使用 C 的数据结构,在实际运用中还可以减少内存的使用。
废话不多说,我的代码放在了 github 上 ,有兴趣的同学可自取。
这个娱乐项目命名为 Ameba ,暗示每个代码单位都足够的小,功能简单。它们必须通过很少的 send/recv 和外界通讯。目前,通讯的数据类型仅限于 number boolean 和 string 。
每个线程(ameba)可以调用 ameba 函数分裂一个新的 ameba 出去。调度器为每个 ameba 分配了一个唯一的通讯通道 (chan) 。ameba 自己可以通过自己的全局变量 chan 拿到这个数字。
读写 chan 可以通过 send / recv 两个 api 。如果返回值为 nil ,则表示 chan 已经被关闭。(目前只可能是 ameba 自己退出死亡)。chan 的读写是阻塞的。即,当你向 chan 写入数据(可以是一个或多个)时,若同时对端 ameba 没有在读取数据,那么写入者将被挂起;反之亦然。
recv 只可以收取系统为其分配的 chan 上的数据。send 则可以制定一个数字表示向哪个 ameba 发送信息。
关于实现:
抢先式多线程是用 lua 的 debug hook 实现的。它在一定程度上会降低 lua 代码执行的性能(不到一倍),可以通过修改时间片的粒度来调整。
每个 ameba 里都有一个 chan 读缓冲区,放在注册表中。当有另外的 ameba 企图写入的时候,首先写到这个缓冲区中,再由本地的 recv 函数复制出来。
整个系统的父 state 中保留有一个表,映射了所有 ameba 的读写队列。用于调度器的工作。这张表存在于父 state 的注册表中。
ameba 之间没有父子层级关系。
这个库是设计成可以递归使用的,可以在 ameba 内重新启动库,这样就可以有层级关系。但,chan id 是一个 C 里的全局变量,会一直累加。当然也可以修改实现,把这个变量放在 lua state 中。
目前的实现中,每个 ameba 的 state 只初始化了 lua 的基础库,没有加载完整的标准库。
自定义的 lua alloc 函数未来用于控制内存分配和管理,目前并没有特别使用。
整块代码娱乐性质为主,也就是写着玩儿。不保证质量。
代码必须装有 lua 5.2 beta 版才可能正常编译,经过少许修改也可以用于 luajit 2 beta 。但由于 lua 早期版本的实现限制,无法用于 lua 5.1 或更早的版本。
Comments
Posted by: 赤道企鹅 | (15) April 29, 2022 06:09 PM
Posted by: 富城 | (14) December 6, 2021 05:25 PM
Posted by: Cloud | (13) December 26, 2015 08:09 PM
Posted by: tsln | (12) December 23, 2015 06:56 PM
Posted by: 小冬 | (11) March 14, 2014 07:11 PM
Posted by: zzz654321 | (10) December 5, 2012 06:02 PM
Posted by: Vincent | (9) November 23, 2011 01:24 PM
Posted by: 高清mv下载 | (8) November 22, 2011 11:08 PM
Posted by: 高低温循环装置 | (7) November 15, 2011 10:18 AM
Posted by: 北京利康搬家公司 | (6) November 15, 2011 10:06 AM
Posted by: 吉老王 | (5) November 14, 2011 12:59 PM
Posted by: hxyman | (4) November 13, 2011 10:06 PM
Posted by: 铁观音茶叶 | (3) November 13, 2011 07:23 PM
Posted by: Also | (2) November 13, 2011 03:55 PM
Posted by: ... | (1) November 12, 2011 08:07 PM