What type of function can be called by Lua
int (*lua_cfunction) (Lua_state *l);
How a function of a conforming type can be called by Lua
Use Lua_register or Lua_pushfunction and Lua_setglobal () to add the function to be called to the Lua state machine.
#define Lua_register (l,n,f)/ (Lua_pushcfunction (L, F), Lua_setglobal (l, N))
The second parameter of Lua_register is the name of the call to this function in the Lua script.
Example: If the C function name is Foo, using Lua_registe to register (L, "Acfoo", foo), then use the Acfoo in the Lua script to represent the use of the Foo function.
How Lua calls the C function is straightforward, using the registered name to call directly
How to pass parameters and calculate results
① Using stack interactions
Quote a passage from the user manual:
Lua uses a virtual stack to pass values to and from C. Each element on the stack is a Lua value (nil, number, string, and so on).
Whenever Lua calls C, the called function gets a new stack, which is independent of the stack of the C function itself, and is independent of the previous stack. (in C functions, the LUA API does not have access to the data in a stack other than this call in the Lua state machine), it contains all the parameters that Lua passes to the C function, and the C function puts the results to be returned into the stack to return to the caller.
For convenience, all API query operations against stacks do not strictly follow the rules of operation of the stack. Instead, you can draw a pointer to any element on the stack: the positive index refers to the absolute position on the stack (from the beginning), and the negative index refers to the offset from the top of the stack. In more detail, if the stack has n elements, then index 1 represents the first element (that is, the element that is first pressed into the stack) and index n refers to the last element; index-1 also refers to the last element (that is, the element at the top of the stack), and index-n refers to the first element. If the index is between 1 and the top of the stack (that is, 1≤abs (index) ≤top) We say that this is a valid index.
② getting parameters from a LUA script
int n = lua_gettop (L); /* */int index ) ....
Index:1-left first argument, 2-left second argument, ...
③ returns the return value
Return in order, Lua accepts in return order
Lua_pushxxx (L, first return value)
Lua_pushxxx (L, second return value)
LUA invokes the C function example:
C Program:
Static intAverage (lua_state *m) { /*get number of arguments*/ intn =lua_gettop (L); Doublesum =0; inti; /*loop through each argument*/ for(i =1; I <= N; i++) { if(!Lua_isnumber (L, i)) {lua_pushstring (L,"incorrect argument to ' average '"); Lua_error (L); } /*Total the arguments*/sum+=Lua_tonumber (L, i); } /*Push the average*/lua_pushnumber (L, Sum/n);//First return value /*Push the sum*/lua_pushnumber (L, sum);//Second return value /*return the number of results*/ return 2;}voidLUACALLC () {/*Initialize Lua*/lua_state) O =Lua_open (); /*load Lua Base libraries*/lual_openlibs (L); /*Register our function*/Lua_register (L,"Average", average); /*Run the script*/lual_dofile (L,"Average.lua"); /*Cleanup Lua*/Lua_close (L);}
Lua script, Average.lua:
AVG, sum = average (+,+,+,)print(" ", avg)print("", sum)
Lua calls from the C library
- Generate C Function library
① all functions that can be called by Lua must be of type lua_cfunction
② all called functions into a lual_reg array
③ a luaopen_* (* indicates the name of the library) to open the library when the LU calls the library
With Lual_register (Lua_state *l,
const Char *libname,
Const LUAL_REG *L)
Libname, registering the use name of LUA when using this library
Lual_reg *l, registers functions in the Lual_reg array in the LUA stack for LUA to invoke
Note: BCB The default exported C function is preceded by an underscore, so adding a def file to the Dynamic Library project does not underline the build. The content is:
Export
Funname = _funname (funname indicates the name of the function to be exported, and the library used by Lua is luaopen_*)
- LUA uses C libraries
Require (libname) – Open library for use
Libname. funname– using the functions provided in the C library
LUA calls the C function library Example:
C library code, the name of the C function "Dllforlua.dll"
static int Lua_msgbox (lua_state* L)
{
Const CHAR* message = lual_checkstring (L, 1);
Const char* caption = Lual_optstring (L, 2, "");
int result = MessageBox (NULL, message, caption, Mb_yesno);
Lua_pushnumber (L, result);
return 1;
}
static const Lual_reg mylib[] =
{
{"MsgBox", Lua_msgbox},
{NULL, NULL}
};
int __declspec (dllexport) Luaopen_dllforlua (lua_state* L)
{
Lual_register (L, "Dllforlua", mylib);
return 1;
}
Lua script, Test.lua
Require ("Dllforlu")
Dllforlua.msgbox ("Hey, it worked!", "Lua Message box");
(iii) C-Tune Lua function
- Initializing the LUA environment
Lua_open or: Lua_newstate
Lual_newstate (call Lua_newstate, and set up a panic function)
- Loading the LUA standard library
Lua_openlibs (open all standard libraries)
Do not open all libraries, open the required libraries:
Luaopen_base
Luaopen_package
Luaopen_string
Luaopen_table
Luaopen_math
..........
- Loading LUA and Function functions
Lual_dofile ()
Lua_getglobal ()
Case sensitive, the function name is exactly the same as the Lua script.
- Press-In Parameters
Different types use different functions to press stacks in order from left to right
Lua_pushnumber,lua_pushstring, ...
- Execute function
Lua_call, Lua_pcall
- Get return value
Different types use different functions, note the index, check the type before getting
- POPs the return value from the stack
Lua_pop ()
- Turn off LUA state machine
Lua_close ()
C program dropped with LUA function example:
C Function:
void Ccalllua ()
{
Create a LUA vmachine
Lua_state *l;
L = Lual_newstate ();
L = Lua_open ();
Load Libraries
Lual_openlibs (L);
Run script/
Lual_dofile (L, "Clua.lua");
Lua_getglobal (L, "Sum");
Lua_pushnumber (l,2);//First parameter
Lua_pushnumber (l,3);//second parameter
Lua_pushnumber (l,4);//A third parameter
Lua_pcall (l,3,2,0);
Double sum=0,ave=0;
if (Lua_isnumber (l,1))
{
Sum=lua_tonumber (l,1);
}
if (Lua_isnumber (l,2))
{
Ave=lua_tonumber (l,2);
}
Lua_pop (l,2);
cout<< "Sum =" <<sum
<< "/nave =" <<ave<<endl;
Clear Lua
Lua_close (L);
GetChar ();
}
Lua Script Clua.lua:
function Sum (...)
Local s=0
Local num=0
For k,v in pairs{...} do
s = s + V
num = k
End
Return S,s/num
End
LUA interacts with C