FFI
更新于 2024-01-09
Foreign Function Interface
FFI库允许纯lua代码调用c函数和结构体
ctype cdata
- ctype是C类型的表示, 允许Lua代码与C数据类型进行交互
- cdata一个特殊的数据类型,它表示 C 数据。
lua
local ffi = require("ffi")
ffi.cdef[[
typedef struct {
int x;
int y;
} Point;
]]
local p = ffi.new("Point") --创建C类型的实例,得到的cdata 对象
p.x = 10
p.y = 20
print(p.x, p.y)
--输出: 10 20
local PointType = ffi.typeof("Point")
print(PointType)
--输出: ctype<struct 97>
local q = PointType()
print(q)
--输出: cdata<struct 97>: 0x7f789aed0f38userdata
Lua调用C
Lua脚本调用C函数
lua
local ffi = require("ffi") --加载FFI库
--申明
ffi.cdef[[
int printf(const char *fmt, ...);
]]
--调用c函数
ffi.C.printf("Hello %s!", "world")
local ffi = require("ffi")
ffi.cdef[[
typedef struct { double x, y; } point_t;
]]
local point
local mt = {
__add = function(a, b) return point(a.x+b.x, a.y+b.y) end,
__len = function(a) return math.sqrt(a.x*a.x + a.y*a.y) end,
__index = {
area = function(a) return a.x*a.x + a.y*a.y end,
},
}
point = ffi.metatype("point_t", mt)
local a = point(3, 4)
print(a.x, a.y) --> 3 4
print(#a) --> 5
print(a:area()) --> 25
local b = a + point(0.5, 8)
print(#b) --> 12.5C调用lua
c语言调用lua文件
c
#include <stdio.h>
#include <lua.h>
#include <lauxlib.h>
#include <lualib.h>
int main(void) {
lua_State *L = luaL_newstate(); /* 创建 Lua 状态机 */
luaL_openlibs(L); /* 打开 Lua 标准库 */
if (luaL_loadfile(L, "script.lua") || lua_pcall(L, 0, 0, 0)) {
/* 如果加载或执行 Lua 脚本出错,打印错误信息 */
fprintf(stderr, "Error: %s\n", lua_tostring(L, -1));
return 1;
}
lua_close(L); /* 关闭 Lua 状态机 */
return 0;
}C语言调用lua,Lua调用C函数
c
#include <stdio.h>
#include <lua.h>
#include <lauxlib.h>
#include <lualib.h>
/* 定义一个 C 函数 */
static int my_add(lua_State *L) {
int a = luaL_checkinteger(L, 1); /* 从 Lua 获取第一个参数 */
int b = luaL_checkinteger(L, 2); /* 从 Lua 获取第二个参数 */
lua_pushinteger(L, a + b); /* 将结果推送到 Lua */
return 1; /* 返回值的数量 */
}
int main(void) {
lua_State *L = luaL_newstate(); /* 创建 Lua 状态机 */
luaL_openlibs(L); /* 打开 Lua 标准库 */
lua_register(L, "my_add", my_add); /* 将 C 函数注册到 Lua */
if (luaL_dostring(L, "print(my_add(10, 20))")) {
/* 如果执行 Lua 代码出错,打印错误信息 */
fprintf(stderr, "Error: %s\n", lua_tostring(L, -1));
return 1;
}
lua_close(L); /* 关闭 Lua 状态机 */
return 0;
}