2 ** $Id: ldblib.c,v 1.5 1999/03/04 21:17:26 roberto Exp $
3 ** Interface from Lua to its debug API
4 ** See Copyright Notice in lua.h
18 static void settabss (lua_Object t
, char *i
, char *v
) {
26 static void settabsi (lua_Object t
, char *i
, int v
) {
34 static lua_Object
getfuncinfo (lua_Object func
) {
35 lua_Object result
= lua_createtable();
38 lua_funcinfo(func
, &str
, &line
);
39 if (line
== -1) /* C function? */
40 settabss(result
, "kind", "C");
41 else if (line
== 0) { /* "main"? */
42 settabss(result
, "kind", "chunk");
43 settabss(result
, "source", str
);
45 else { /* Lua function */
46 settabss(result
, "kind", "Lua");
47 settabsi(result
, "def_line", line
);
48 settabss(result
, "source", str
);
50 if (line
!= 0) { /* is it not a "main"? */
51 char *kind
= lua_getobjname(func
, &str
);
53 settabss(result
, "name", str
);
54 settabss(result
, "where", kind
);
61 static void getstack (void) {
62 lua_Object func
= lua_stackedfunction(luaL_check_int(1));
63 if (func
== LUA_NOOBJECT
) /* level out of range? */
66 lua_Object result
= getfuncinfo(func
);
67 int currline
= lua_currentline(func
);
69 settabsi(result
, "current", currline
);
70 lua_pushobject(result
);
71 lua_pushstring("func");
73 lua_settable(); /* result.func = func */
74 lua_pushobject(result
);
79 static void funcinfo (void) {
80 lua_pushobject(getfuncinfo(luaL_functionarg(1)));
84 static int findlocal (lua_Object func
, int arg
) {
85 lua_Object v
= lua_getparam(arg
);
87 return (int)lua_getnumber(v
);
89 char *name
= luaL_check_string(arg
);
93 while (lua_getlocal(func
, ++i
, &vname
) != LUA_NOOBJECT
) {
94 if (strcmp(name
, vname
) == 0)
95 result
= i
; /* keep looping to get the last var with this name */
98 luaL_verror("no local variable `%.50s' at given level", name
);
104 static void getlocal (void) {
105 lua_Object func
= lua_stackedfunction(luaL_check_int(1));
108 if (func
== LUA_NOOBJECT
) /* level out of range? */
109 return; /* return nil */
110 else if (lua_getparam(2) != LUA_NOOBJECT
) { /* 2nd argument? */
111 if ((val
= lua_getlocal(func
, findlocal(func
, 2), &name
)) != LUA_NOOBJECT
) {
113 lua_pushstring(name
);
115 /* else return nil */
117 else { /* collect all locals in a table */
118 lua_Object result
= lua_createtable();
121 if ((val
= lua_getlocal(func
, i
, &name
)) == LUA_NOOBJECT
)
123 lua_pushobject(result
);
124 lua_pushstring(name
);
126 lua_settable(); /* result[name] = value */
128 lua_pushobject(result
);
133 static void setlocal (void) {
134 lua_Object func
= lua_stackedfunction(luaL_check_int(1));
136 luaL_arg_check(func
!= LUA_NOOBJECT
, 1, "level out of range");
137 numvar
= findlocal(func
, 2);
138 lua_pushobject(luaL_nonnullarg(3));
139 if (!lua_setlocal(func
, numvar
))
140 lua_error("no such local variable");
145 static int linehook
= -1; /* Lua reference to line hook function */
146 static int callhook
= -1; /* Lua reference to call hook function */
149 static void dohook (int ref
) {
150 lua_LHFunction oldlinehook
= lua_setlinehook(NULL
);
151 lua_CHFunction oldcallhook
= lua_setcallhook(NULL
);
152 lua_callfunction(lua_getref(ref
));
153 lua_setlinehook(oldlinehook
);
154 lua_setcallhook(oldcallhook
);
158 static void linef (int line
) {
159 lua_pushnumber(line
);
164 static void callf (lua_Function func
, char *file
, int line
) {
165 if (func
!= LUA_NOOBJECT
) {
166 lua_pushobject(func
);
167 lua_pushstring(file
);
168 lua_pushnumber(line
);
174 static void setcallhook (void) {
175 lua_Object f
= lua_getparam(1);
177 if (f
== LUA_NOOBJECT
) {
179 lua_setcallhook(NULL
);
183 callhook
= lua_ref(1);
184 lua_setcallhook(callf
);
189 static void setlinehook (void) {
190 lua_Object f
= lua_getparam(1);
192 if (f
== LUA_NOOBJECT
) {
194 lua_setlinehook(NULL
);
198 linehook
= lua_ref(1);
199 lua_setlinehook(linef
);
204 static struct luaL_reg dblib
[] = {
205 {"funcinfo", funcinfo
},
206 {"getlocal", getlocal
},
207 {"getstack", getstack
},
208 {"setcallhook", setcallhook
},
209 {"setlinehook", setlinehook
},
210 {"setlocal", setlocal
}
214 void lua_dblibopen (void) {
215 luaL_openlib(dblib
, (sizeof(dblib
)/sizeof(dblib
[0])));