Imported from ../lua-3.0.tar.gz.
[lua.git] / src / func.c
blob36f7e19fa6288b7948941d98a11e54b1d6453b4b
1 #include <string.h>
3 #include "luadebug.h"
4 #include "table.h"
5 #include "luamem.h"
6 #include "func.h"
7 #include "opcode.h"
8 #include "inout.h"
11 static TFunc *function_root = NULL;
12 static LocVar *currvars = NULL;
13 static int numcurrvars = 0;
14 static int maxcurrvars = 0;
18 ** Initialize TFunc struct
20 void luaI_initTFunc (TFunc *f)
22 f->next = NULL;
23 f->marked = 0;
24 f->size = 0;
25 f->code = NULL;
26 f->lineDefined = 0;
27 f->fileName = lua_parsedfile;
28 f->locvars = NULL;
32 ** Insert function in list for GC
34 void luaI_insertfunction (TFunc *f)
36 lua_pack();
37 f->next = function_root;
38 function_root = f;
39 f->marked = 0;
44 ** Free function
46 void luaI_freefunc (TFunc *f)
48 luaI_free (f->code);
49 luaI_free (f->locvars);
50 luaI_free (f);
54 void luaI_funcfree (TFunc *l)
56 while (l) {
57 TFunc *next = l->next;
58 luaI_freefunc(l);
59 l = next;
64 ** Garbage collection function.
66 TFunc *luaI_funccollector (long *acum)
68 TFunc *curr = function_root;
69 TFunc *prev = NULL;
70 TFunc *frees = NULL;
71 long counter = 0;
72 while (curr) {
73 TFunc *next = curr->next;
74 if (!curr->marked) {
75 if (prev == NULL)
76 function_root = next;
77 else
78 prev->next = next;
79 curr->next = frees;
80 frees = curr;
81 ++counter;
83 else {
84 curr->marked = 0;
85 prev = curr;
87 curr = next;
89 *acum += counter;
90 return frees;
94 void lua_funcinfo (lua_Object func, char **filename, int *linedefined)
96 TObject *f = luaI_Address(func);
97 if (f->ttype == LUA_T_MARK || f->ttype == LUA_T_FUNCTION)
99 *filename = f->value.tf->fileName;
100 *linedefined = f->value.tf->lineDefined;
102 else if (f->ttype == LUA_T_CMARK || f->ttype == LUA_T_CFUNCTION)
104 *filename = "(C)";
105 *linedefined = -1;
110 ** Stores information to know that variable has been declared in given line
112 void luaI_registerlocalvar (TaggedString *varname, int line)
114 if (numcurrvars >= maxcurrvars)
115 maxcurrvars = growvector(&currvars, maxcurrvars, LocVar, "", MAX_WORD);
116 currvars[numcurrvars].varname = varname;
117 currvars[numcurrvars].line = line;
118 numcurrvars++;
122 ** Stores information to know that variable has been out of scope in given line
124 void luaI_unregisterlocalvar (int line)
126 luaI_registerlocalvar(NULL, line);
130 ** Copies "currvars" into a new area and store it in function header.
131 ** The values (varname = NULL, line = -1) signal the end of vector.
133 void luaI_closelocalvars (TFunc *func)
135 func->locvars = newvector (numcurrvars+1, LocVar);
136 memcpy (func->locvars, currvars, numcurrvars*sizeof(LocVar));
137 func->locvars[numcurrvars].varname = NULL;
138 func->locvars[numcurrvars].line = -1;
139 numcurrvars = 0; /* prepares for next function */
143 ** Look for n-esim local variable at line "line" in function "func".
144 ** Returns NULL if not found.
146 char *luaI_getlocalname (TFunc *func, int local_number, int line)
148 int count = 0;
149 char *varname = NULL;
150 LocVar *lv = func->locvars;
151 if (lv == NULL)
152 return NULL;
153 for (; lv->line != -1 && lv->line < line; lv++)
155 if (lv->varname) /* register */
157 if (++count == local_number)
158 varname = lv->varname->str;
160 else /* unregister */
161 if (--count < local_number)
162 varname = NULL;
164 return varname;