Ubuntu Lua calls C functions.

      Lua has been used for a long time, for framework reasons, today I will write about how Lua calls the so library.

      I really don’t know if I don’t do it. It’s amazing to do it. So many articles on the Internet, basically you copy me, I copy you. The errors are the same, and the verification has not been verified. . .

      First declare my environment, Ubuntu 18.04, lua5.3

1. Concept supplement, Lua and C interact through a virtual stack, why is this?

The key content of communication between C and Lua is a virtual stack. Almost all calls are to operate on values ​​on the stack, and all data exchanges between C and Lua are also done through this stack. In addition, you can also use the stack to store temporary variables. Every C function that communicates with Lua has its own virtual stack, which is managed by Lua.
The use of the stack solves the two inconsistencies between C and Lua: First, Lua will automatically perform garbage collection, while C requires explicit allocation of storage units, which causes the contradiction between the two. Second, the confusion caused by the inconsistency between the dynamic types in Lua and the static types in C.

2. To call the method in C, you need to compile C into a dynamic library, I am under linux, so it is .so, the code is as follows

c_so.cpp

extern "C" {
  #include <stdio.h>
  #include <lua.h>
  #include <lualib.h>
  #include <lauxlib.h>
}
 
 
//自定义函数
static int my_add(lua_State *L)
{
    int x = lua_tonumber(L,1); //第一个参数,转换为数字
    int y = lua_tonumber(L,2); //第二个参数,转换为数字
    int sum = x + y;           
    lua_pushnumber(L, sum);    //将函数的结果压入栈中。如果有多个返回值,可以在这里多次压入栈中。
    return 1; //返回sum计算结果
}
 
static int showstr(lua_State *L)
{
   //从lua中传入的第一个参数
   const char *str = lua_tostring (L, 1);
 
   printf ("c program str = %s\n", str);
   return 0;
}
 
/* 需要一个"luaL_Reg"类型的结构体,其中每一个元素对应一个提供给Lua的函数。
 * 每一个元素中包含此函数在Lua中的名字,以及该函数在C库中的函数指针。
 * 最后一个元素为“哨兵元素”(两个"NULL"),用于告诉Lua没有其他的函数需要注册。
 */
static luaL_Reg funclist[] =
{
    {"add", my_add}, //my_add()函数,lua中访问时使用名称为add
    {"show", showstr}, //showstr()函数,lua中访问时使用名称为show
    {NULL, NULL},  //最后必须有这个
};
 
/* 此函数为C库中的“特殊函数”。
 * 通过调用它注册所有C库中的函数,并将它们存储在适当的位置。
 * 此函数的命名规则应遵循:
 * 1、使用"luaopen_"作为前缀。
 * 2、前缀之后的名字将作为"require"的参数。
 */
extern "C" int luaopen_mylib(lua_State *L )
{
     /* void luaL_newlib (lua_State *L, const luaL_Reg l[]);
     * 创建一个新的"table",并将"l"中所列出的函数注册为"table"的域。
     */ 
    luaL_newlib(L, funclist);
    return 1;
}

Then compile  gcc -shared -fPIC c_so.cpp -o mylib.so -I /home/lk/my_skynet_learning/skynet/3rd/lua/

After compiling, you will get mylib.so

testso.lua

local mylib = require "mylib"

local i = mylib.add(1, 2)
print(i)

local j = mylib.show('真的太多坑了')

The results are as follows

 

The online search is really all kinds of pits. Hey.

Guess you like

Origin blog.csdn.net/banfushen007/article/details/108984748