elisp似乎并没有关注是否应该实现一套标准的elisp cffi。
我不清楚emacs module机制出现的确切时间,但是module机制或许减弱了对ffi的需求。我发现了一些很早的项目,这些工作致力于在emacs中实现一套可用的cffi:
emacs-with-ffi 是基于emacs 25的源码补丁,为emacs增加了ffi feature,但是存在内存泄漏和崩溃等问题,作者在提交了最后一个名为no idea
的补丁之后弃坑了。
elisp-ffi用cpp实现了一个简单的胶水,直接通过读写std流进行交互。因此,它不需要改造emacs,是一个有趣的小玩具。
emacs-ffi基于emacs module和libffi实现,看上去是里面设计最好的一个了,但是在7年前也停止了维护。
通过比较这些项目,我认为实现ffi接口面临的主要问题是:
- 实现安全的参数传递,这需要正确的类型转译以及对象生命周期管理。对于潜在的同步问题需要提供对应的同步机制(这可能会非常困难)。
- 实现错误处理机制,当函数调用失败时可以捕获错误,不应该导致调用者挂死。
上述实现都只是简单地实现了类型转译和函数接口的封装。从issue来看,它们对于内存和线程同步问题都存在不同程度的明显的bug,也没有专门设计任何错误处理。
Guile Emacs似乎是唯一把这些问题纳入考量的。虽然它的目的不是实现ffi,而是elisp到guile的翻译器。这件事比实现cffi要困难得多,它的目标差不多是用scheme实现emacs,尽管原有的c代码对guile是透明的,但是它们本身有不同的内存布局和工作机制。目前这个项目处于停滞状态。
在某些我们觉得对lisp理所当然的事情上,elisp似乎已经无法跟上了……