您的位置:首页 > 编程语言 > Lua

LUA 源码阅读笔记(一)

2011-11-08 11:37 253 查看
好久没有在网上留言了。。。

背景介绍

因为工作的需要,后台svr要能够动态修改更新,使用C当然没有问题,问题就在于修改源码后,需要重启服务。所以就想到在C里能够嵌入一种脚本,最好是和C无缝结合的。因此就想到使用到LUA,LUA的大名圈内人士应该早有耳闻,只不过一直没有机会接触。机缘巧合,有幸一见。

俗话说得好,耳闻不如一见。LUA使用起来还是很简单的,语法和普通的脚本语言相差不大,很容易上手。在实际项目的使用过程中,对LUA性能的体验也是感受尤深。这也是决定一探LUA源码的动力所在。因此,本笔记也只是针对LUA源码的相关记录,不会涉及到LUA使用上的一些问题。同时,也欢迎各位LUA爱好者批评指正笔记中的错误之处。废话不说了,切入正题。

(1)mathlib strlib

mathlib 和 strlib是lua的一个基本库,每个函数的实现都是在在基本库的基础上重新封装,举个例子

static int math_abs (lua_State *L) {
lua_pushnumber(L, fabs(luaL_checknumber(L, 1)));
return 1;
}


调用基本库fabs()函数,将返回的结果压栈返回。那肯定有一个疑问,就是参数怎么传递进去的?是呀,参数怎么传递进去的,我现在也不知道,但是不要紧,先有个印象就行。

还要明白一点,外界不会直接调用math_abs(),为什么?static呀,如果不明白的,先修炼一下C的基本功吧,下面继续来猜测外面怎么调用这些函数。

static const luaL_Reg mathlib[] = {
{"abs",   math_abs},
{"acos",  math_acos},
{"asin",  math_asin},
{"atan2", math_atan2},
{"atan",  math_atan},
{"ceil",  math_ceil},
{"cosh",   math_cosh},
{"cos",   math_cos},
{"deg",   math_deg},
{"exp",   math_exp},
{"floor", math_floor},
{"fmod",   math_fmod},
{"frexp", math_frexp},
{"ldexp", math_ldexp},
{"log10", math_log10},
{"log",   math_log},
{"max",   math_max},
{"min",   math_min},
{"modf",   math_modf},
{"pow",   math_pow},
{"rad",   math_rad},
{"random",     math_random},
{"randomseed", math_randomseed},
{"sinh",   math_sinh},
{"sin",   math_sin},
{"sqrt",  math_sqrt},
{"tanh",   math_tanh},
{"tan",   math_tan},
{NULL, NULL}
};


上面这个结构体定义了内部函数名(或者是函数指针)与外部函数名之间的映射关系,比如要调用math_abs(),那实际使用的就是abs()来调用,目前,这还是猜测,是不是这样还有待验证。

那luaL_Reg 是啥,看如下声明:

typedef struct luaL_Reg {
const char *name;
lua_CFunction func;
} luaL_Reg;


就是一个名字,和一个函数指针,

typedef int (*lua_CFunction) (lua_State *L);


lua如何将这个映射注册进去呢,看下面的函数,这个是mathlib的外部唯一接口

LUALIB_API int luaopen_math (lua_State *L) {
luaL_register(L, LUA_MATHLIBNAME, mathlib);
lua_pushnumber(L, PI);
lua_setfield(L, -2, "pi");
lua_pushnumber(L, HUGE_VAL);
lua_setfield(L, -2, "huge");
#if defined(LUA_COMPAT_MOD)
lua_getfield(L, -1, "fmod");
lua_setfield(L, -2, "mod");
#endif
return 1;
}


大概的意思就是将mathlib这个luaL_Reg对象在L中注册登记,L是什么,L就是lua_State*!!!!!等于没说,但是目前的认知也就是这些,这是最准确的表述,不是吗?从名字上看,应该是一个状态机。想知道到底是什么,接着看代码。注册登记完了,将一些常量压栈。应该是设置一些环境变量,等等。

strlib和mathlib的结构差不多,

也是重新封装一大堆函数,然后通过一个唯一接口来注册所有的函数。实际使用的时候,也就是调用这个唯一的接口。调用完该接口,应该就可以在那个叫做lua_State*的L中使用这些基本库函数了。

到目前为止,很多还是不确定的,比如lua_State是什么,为什么基本库的注册登记,都要向针对这个L进行。L中到底维护的是什么信息,翻开lua_State的定义,一大堆数据,很多都不知道是什么。好吧,先不看这个,先继续看别的,但是要知道这个就是一个结构体就行,这个结构体里面肯定维护很多核心的东西。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: