no more special cases for closures with 0 upvalues (performance is the same,

memory use a little higher, code much simpler).
This commit is contained in:
Roberto Ierusalimschy 2000-03-29 17:19:20 -03:00
parent b53dc0c485
commit a69356e9e0
16 changed files with 128 additions and 194 deletions

23
lapi.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: lapi.c,v 1.75 2000/03/20 19:14:54 roberto Exp roberto $ ** $Id: lapi.c,v 1.76 2000/03/27 20:10:21 roberto Exp roberto $
** Lua API ** Lua API
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -30,17 +30,6 @@ const char lua_ident[] = "$Lua: " LUA_VERSION " " LUA_COPYRIGHT " $\n"
const TObject *luaA_protovalue (const TObject *o) {
switch (ttype(o)) {
case TAG_CCLOSURE: case TAG_LCLOSURE:
return protovalue(o);
default:
return o;
}
}
void luaA_checkCargs (lua_State *L, int nargs) { void luaA_checkCargs (lua_State *L, int nargs) {
if (nargs > L->top-L->Cstack.base) if (nargs > L->top-L->Cstack.base)
luaL_verror(L, "Lua API error - " luaL_verror(L, "Lua API error - "
@ -210,7 +199,8 @@ int lua_isuserdata (lua_State *L, lua_Object o) {
} }
int lua_iscfunction (lua_State *L, lua_Object o) { int lua_iscfunction (lua_State *L, lua_Object o) {
return (lua_tag(L, o) == TAG_CPROTO); UNUSED(L);
return (o != LUA_NOOBJECT) && (ttype(o) == TAG_CCLOSURE);
} }
int lua_isnumber (lua_State *L, lua_Object o) { int lua_isnumber (lua_State *L, lua_Object o) {
@ -266,7 +256,7 @@ void *lua_getuserdata (lua_State *L, lua_Object obj) {
lua_CFunction lua_getcfunction (lua_State *L, lua_Object obj) { lua_CFunction lua_getcfunction (lua_State *L, lua_Object obj) {
if (!lua_iscfunction(L, obj)) if (!lua_iscfunction(L, obj))
return NULL; return NULL;
else return fvalue(luaA_protovalue(obj)); else return clvalue(obj)->f.c;
} }
@ -299,10 +289,7 @@ void lua_pushcclosure (lua_State *L, lua_CFunction fn, int n) {
if (fn == NULL) if (fn == NULL)
lua_error(L, "Lua API error - attempt to push a NULL Cfunction"); lua_error(L, "Lua API error - attempt to push a NULL Cfunction");
luaA_checkCargs(L, n); luaA_checkCargs(L, n);
ttype(L->top) = TAG_CPROTO; luaV_Cclosure(L, fn, n);
fvalue(L->top) = fn;
incr_top;
luaV_closure(L, n);
luaC_checkGC(L); luaC_checkGC(L);
} }

3
lapi.h
View File

@ -1,5 +1,5 @@
/* /*
** $Id: lapi.h,v 1.14 2000/03/03 14:58:26 roberto Exp roberto $ ** $Id: lapi.h,v 1.15 2000/03/10 18:37:44 roberto Exp roberto $
** Auxiliary functions from Lua API ** Auxiliary functions from Lua API
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -12,7 +12,6 @@
void luaA_checkCargs (lua_State *L, int nargs); void luaA_checkCargs (lua_State *L, int nargs);
const TObject *luaA_protovalue (const TObject *o);
void luaA_pushobject (lua_State *L, const TObject *o); void luaA_pushobject (lua_State *L, const TObject *o);
GlobalVar *luaA_nextvar (lua_State *L, TString *g); GlobalVar *luaA_nextvar (lua_State *L, TString *g);
int luaA_next (lua_State *L, const Hash *t, int i); int luaA_next (lua_State *L, const Hash *t, int i);

View File

@ -1,5 +1,5 @@
/* /*
** $Id: lbuiltin.c,v 1.98 2000/03/27 20:08:02 roberto Exp roberto $ ** $Id: lbuiltin.c,v 1.99 2000/03/27 20:10:21 roberto Exp roberto $
** Built-in functions ** Built-in functions
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -386,12 +386,6 @@ void luaB_tostring (lua_State *L) {
case TAG_LCLOSURE: case TAG_CCLOSURE: case TAG_LCLOSURE: case TAG_CCLOSURE:
sprintf(buff, "function: %p", o->value.cl); sprintf(buff, "function: %p", o->value.cl);
break; break;
case TAG_LPROTO:
sprintf(buff, "function: %p", o->value.tf);
break;
case TAG_CPROTO:
sprintf(buff, "function: %p", o->value.f);
break;
case TAG_USERDATA: case TAG_USERDATA:
sprintf(buff, "userdata: %p(%d)", o->value.ts->u.d.value, sprintf(buff, "userdata: %p(%d)", o->value.ts->u.d.value,
o->value.ts->u.d.tag); o->value.ts->u.d.tag);

View File

@ -1,5 +1,5 @@
/* /*
** $Id: ldebug.c,v 1.12 2000/03/20 19:14:54 roberto Exp roberto $ ** $Id: ldebug.c,v 1.13 2000/03/27 20:10:21 roberto Exp roberto $
** Debug Interface ** Debug Interface
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -24,10 +24,8 @@
static const lua_Type normtype[] = { /* ORDER LUA_T */ static const lua_Type normtype[] = { /* ORDER LUA_T */
TAG_USERDATA, TAG_NUMBER, TAG_STRING, TAG_TABLE, TAG_USERDATA, TAG_NUMBER, TAG_STRING, TAG_TABLE,
TAG_LPROTO, TAG_CPROTO, TAG_NIL, TAG_LCLOSURE, TAG_CCLOSURE, TAG_NIL,
TAG_LCLOSURE, TAG_CCLOSURE, TAG_LCLOSURE, TAG_CCLOSURE /* TAG_LCLMARK, TAG_CCLMARK */
TAG_LCLOSURE, TAG_CCLOSURE, /* TAG_LCLMARK, TAG_CCLMARK */
TAG_LPROTO, TAG_CPROTO /* TAG_LMARK, TAG_CMARK */
}; };
@ -104,11 +102,7 @@ static int lua_currentline (lua_State *L, StkId f) {
static Proto *getluaproto (StkId f) { static Proto *getluaproto (StkId f) {
if (ttype(f) == TAG_LMARK) return (ttype(f) == TAG_LCLMARK) ? clvalue(f)->f.l : NULL;
return f->value.tf;
else if (ttype(f) == TAG_LCLMARK)
return protovalue(f)->value.tf;
else return NULL;
} }
@ -141,20 +135,18 @@ int lua_setlocal (lua_State *L, const lua_Dbgactreg *ar, lua_Dbglocvar *v) {
static void lua_funcinfo (lua_Dbgactreg *ar) { static void lua_funcinfo (lua_Dbgactreg *ar) {
StkId func = ar->_func; StkId func = ar->_func;
switch (ttype(func)) { switch (ttype(func)) {
case TAG_LPROTO: case TAG_LMARK:
ar->source = tfvalue(func)->source->str;
ar->linedefined = tfvalue(func)->lineDefined;
ar->what = "Lua";
break;
case TAG_LCLOSURE: case TAG_LCLMARK: case TAG_LCLOSURE: case TAG_LCLMARK:
ar->source = tfvalue(protovalue(func))->source->str; ar->source = clvalue(func)->f.l->source->str;
ar->linedefined = tfvalue(protovalue(func))->lineDefined; ar->linedefined = clvalue(func)->f.l->lineDefined;
ar->what = "Lua"; ar->what = "Lua";
break; break;
default: case TAG_CCLOSURE: case TAG_CCLMARK:
ar->source = "(C)"; ar->source = "(C)";
ar->linedefined = -1; ar->linedefined = -1;
ar->what = "C"; ar->what = "C";
break;
default:
LUA_INTERNALERROR(L, "invalid `func' value");
} }
if (ar->linedefined == 0) if (ar->linedefined == 0)
ar->what = "main"; ar->what = "main";

63
ldo.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: ldo.c,v 1.68 2000/03/03 14:58:26 roberto Exp roberto $ ** $Id: ldo.c,v 1.69 2000/03/10 18:37:44 roberto Exp roberto $
** Stack and Call structure of Lua ** Stack and Call structure of Lua
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -119,7 +119,7 @@ void luaD_lineHook (lua_State *L, StkId func, int line) {
} }
void luaD_callHook (lua_State *L, StkId func, lua_Dbghook callhook, static void luaD_callHook (lua_State *L, StkId func, lua_Dbghook callhook,
const char *event) { const char *event) {
if (L->allowhooks) { if (L->allowhooks) {
lua_Dbgactreg ar; lua_Dbgactreg ar;
@ -137,40 +137,31 @@ void luaD_callHook (lua_State *L, StkId func, lua_Dbghook callhook,
} }
/* static StkId callCclosure (lua_State *L, const struct Closure *cl, StkId base) {
** Call a C function. int nup = cl->nelems; /* number of upvalues */
** Cstack.num is the number of arguments; Cstack.lua2C points to the int numarg = L->top-base;
** first argument. Returns an index to the first result from C.
*/
static StkId callC (lua_State *L, lua_CFunction f, StkId base) {
struct C_Lua_Stack oldCLS = L->Cstack; struct C_Lua_Stack oldCLS = L->Cstack;
StkId firstResult; StkId firstResult;
int numarg = L->top - base; if (nup > 0) {
int n = numarg;
luaD_checkstack(L, nup);
/* open space for upvalues as extra arguments */
while (n--) *(base+nup+n) = *(base+n);
L->top += nup;
numarg += nup;
/* copy upvalues into stack */
while (nup--) *(base+nup) = cl->consts[nup];
}
L->Cstack.num = numarg; L->Cstack.num = numarg;
L->Cstack.lua2C = base; L->Cstack.lua2C = base;
L->Cstack.base = L->top; L->Cstack.base = L->top;
if (L->callhook) (*cl->f.c)(L); /* do the actual call */
luaD_callHook(L, base-1, L->callhook, "call");
(*f)(L); /* do the actual call */
firstResult = L->Cstack.base; firstResult = L->Cstack.base;
L->Cstack = oldCLS; L->Cstack = oldCLS;
return firstResult; return firstResult;
} }
static StkId callCclosure (lua_State *L, const struct Closure *cl, StkId base) {
int nup = cl->nelems; /* number of upvalues */
int n = L->top-base; /* number of arguments (to move up) */
luaD_checkstack(L, nup);
/* open space for upvalues as extra arguments */
while (n--) *(base+nup+n) = *(base+n);
L->top += nup;
/* copy upvalues into stack */
while (nup--) *(base+nup) = cl->consts[nup+1];
return callC(L, fvalue(cl->consts), base);
}
void luaD_callTM (lua_State *L, const TObject *f, int nParams, int nResults) { void luaD_callTM (lua_State *L, const TObject *f, int nParams, int nResults) {
StkId base = L->top - nParams; StkId base = L->top - nParams;
luaD_openstack(L, base); luaD_openstack(L, base);
@ -191,24 +182,18 @@ void luaD_call (lua_State *L, StkId func, int nResults) {
lua_Dbghook callhook = L->callhook; lua_Dbghook callhook = L->callhook;
retry: /* for `function' tag method */ retry: /* for `function' tag method */
switch (ttype(func)) { switch (ttype(func)) {
case TAG_CPROTO:
ttype(func) = TAG_CMARK;
firstResult = callC(L, fvalue(func), func+1);
break;
case TAG_LPROTO:
ttype(func) = TAG_LMARK;
firstResult = luaV_execute(L, NULL, tfvalue(func), func+1);
break;
case TAG_LCLOSURE: { case TAG_LCLOSURE: {
Closure *c = clvalue(func);
ttype(func) = TAG_LCLMARK; ttype(func) = TAG_LCLMARK;
firstResult = luaV_execute(L, c, tfvalue(c->consts), func+1); if (callhook)
luaD_callHook(L, func, callhook, "call");
firstResult = luaV_execute(L, clvalue(func), func+1);
break; break;
} }
case TAG_CCLOSURE: { case TAG_CCLOSURE: {
Closure *c = clvalue(func);
ttype(func) = TAG_CCLMARK; ttype(func) = TAG_CCLMARK;
firstResult = callCclosure(L, c, func+1); if (callhook)
luaD_callHook(L, func, callhook, "call");
firstResult = callCclosure(L, clvalue(func), func+1);
break; break;
} }
default: { /* `func' is not a function; check the `function' tag method */ default: { /* `func' is not a function; check the `function' tag method */
@ -316,9 +301,7 @@ static int protectedparser (lua_State *L, ZIO *z, int bin) {
L->errorJmp = oldErr; L->errorJmp = oldErr;
if (status) return 1; /* error code */ if (status) return 1; /* error code */
if (tf == NULL) return 2; /* `natural' end */ if (tf == NULL) return 2; /* `natural' end */
L->top->ttype = TAG_LPROTO; /* push new function on the stack */ luaV_Lclosure(L, tf, 0);
L->top->value.tf = tf;
incr_top;
return 0; return 0;
} }

4
ldo.h
View File

@ -1,5 +1,5 @@
/* /*
** $Id: ldo.h,v 1.17 2000/01/19 12:00:45 roberto Exp roberto $ ** $Id: ldo.h,v 1.18 2000/03/24 17:26:08 roberto Exp roberto $
** Stack and Call structure of Lua ** Stack and Call structure of Lua
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -22,8 +22,6 @@
void luaD_init (lua_State *L, int stacksize); void luaD_init (lua_State *L, int stacksize);
void luaD_adjusttop (lua_State *L, StkId base, int extra); void luaD_adjusttop (lua_State *L, StkId base, int extra);
void luaD_openstack (lua_State *L, StkId pos); void luaD_openstack (lua_State *L, StkId pos);
void luaD_callHook (lua_State *L, StkId func, lua_Dbghook callhook,
const char *event);
void luaD_lineHook (lua_State *L, StkId func, int line); void luaD_lineHook (lua_State *L, StkId func, int line);
void luaD_call (lua_State *L, StkId func, int nResults); void luaD_call (lua_State *L, StkId func, int nResults);
void luaD_callTM (lua_State *L, const TObject *f, int nParams, int nResults); void luaD_callTM (lua_State *L, const TObject *f, int nParams, int nResults);

View File

@ -1,5 +1,5 @@
/* /*
** $Id: lfunc.c,v 1.19 2000/03/03 14:58:26 roberto Exp roberto $ ** $Id: lfunc.c,v 1.20 2000/03/10 18:37:44 roberto Exp roberto $
** Auxiliary functions to manipulate prototypes and closures ** Auxiliary functions to manipulate prototypes and closures
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -19,7 +19,8 @@
Closure *luaF_newclosure (lua_State *L, int nelems) { Closure *luaF_newclosure (lua_State *L, int nelems) {
Closure *c = (Closure *)luaM_malloc(L, sizeof(Closure)+nelems*sizeof(TObject)); Closure *c = (Closure *)luaM_malloc(L, sizeof(Closure) +
sizeof(TObject)*(nelems-1));
c->next = L->rootcl; c->next = L->rootcl;
L->rootcl = c; L->rootcl = c;
c->marked = 0; c->marked = 0;

15
lgc.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: lgc.c,v 1.43 2000/03/27 20:08:02 roberto Exp roberto $ ** $Id: lgc.c,v 1.44 2000/03/27 20:10:21 roberto Exp roberto $
** Garbage Collector ** Garbage Collector
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -43,9 +43,9 @@ static void protomark (lua_State *L, Proto *f) {
static void closuremark (lua_State *L, Closure *f) { static void closuremark (lua_State *L, Closure *f) {
if (!f->marked) { if (!f->marked) {
int i; int i = f->nelems;
f->marked = 1; f->marked = 1;
for (i=f->nelems; i>=0; i--) while (i--)
markobject(L, &f->consts[i]); markobject(L, &f->consts[i]);
} }
} }
@ -103,13 +103,12 @@ static int markobject (lua_State *L, TObject *o) {
hashmark(L, avalue(o)); hashmark(L, avalue(o));
break; break;
case TAG_LCLOSURE: case TAG_LCLMARK: case TAG_LCLOSURE: case TAG_LCLMARK:
protomark(L, clvalue(o)->f.l);
/* go trhough */
case TAG_CCLOSURE: case TAG_CCLMARK: case TAG_CCLOSURE: case TAG_CCLMARK:
closuremark(L, o->value.cl); closuremark(L, clvalue(o));
break; break;
case TAG_LPROTO: case TAG_LMARK: default: break; /* numbers, etc */
protomark(L, o->value.tf);
break;
default: break; /* numbers, cprotos, etc */
} }
return 0; return 0;
} }

View File

@ -1,5 +1,5 @@
/* /*
** $Id: lobject.c,v 1.33 2000/03/10 18:37:44 roberto Exp roberto $ ** $Id: lobject.c,v 1.34 2000/03/27 20:10:21 roberto Exp roberto $
** Some generic functions over Lua objects ** Some generic functions over Lua objects
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -15,8 +15,7 @@
const char *const luaO_typenames[] = { /* ORDER LUA_T */ const char *const luaO_typenames[] = { /* ORDER LUA_T */
"userdata", "number", "string", "table", "function", "function", "nil", "userdata", "number", "string", "table", "function", "function", "nil",
"function", "function", "function", "function", "function", "function", "function", "function", "line"
"line", NULL
}; };
@ -35,20 +34,16 @@ unsigned long luaO_power2 (unsigned long n) {
int luaO_equalval (const TObject *t1, const TObject *t2) { int luaO_equalval (const TObject *t1, const TObject *t2) {
switch (ttype(t1)) { switch (ttype(t1)) {
case TAG_NIL:
return 1;
case TAG_NUMBER: case TAG_NUMBER:
return nvalue(t1) == nvalue(t2); return nvalue(t1) == nvalue(t2);
case TAG_STRING: case TAG_USERDATA: case TAG_STRING: case TAG_USERDATA:
return svalue(t1) == svalue(t2); return svalue(t1) == svalue(t2);
case TAG_TABLE: case TAG_TABLE:
return avalue(t1) == avalue(t2); return avalue(t1) == avalue(t2);
case TAG_LPROTO:
return tfvalue(t1) == tfvalue(t2);
case TAG_CPROTO:
return fvalue(t1) == fvalue(t2);
case TAG_CCLOSURE: case TAG_LCLOSURE: case TAG_CCLOSURE: case TAG_LCLOSURE:
return t1->value.cl == t2->value.cl; return clvalue(t1) == clvalue(t2);
case TAG_NIL:
return 1;
default: default:
LUA_INTERNALERROR(L, "invalid type"); LUA_INTERNALERROR(L, "invalid type");
return 0; /* UNREACHABLE */ return 0; /* UNREACHABLE */

View File

@ -1,5 +1,5 @@
/* /*
** $Id: lobject.h,v 1.55 2000/03/24 19:49:23 roberto Exp roberto $ ** $Id: lobject.h,v 1.56 2000/03/27 20:10:21 roberto Exp roberto $
** Type definitions for Lua objects ** Type definitions for Lua objects
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -23,7 +23,12 @@
#endif #endif
#ifdef DEBUG
/* to avoid warnings and make sure is is really unused */
#define UNUSED(x) (x=0, (void)x)
#else
#define UNUSED(x) (void)x /* to avoid warnings */ #define UNUSED(x) (void)x /* to avoid warnings */
#endif
/* /*
@ -36,17 +41,12 @@ typedef enum {
TAG_NUMBER, /* fixed tag for numbers */ TAG_NUMBER, /* fixed tag for numbers */
TAG_STRING, /* fixed tag for strings */ TAG_STRING, /* fixed tag for strings */
TAG_TABLE, /* default tag for tables */ TAG_TABLE, /* default tag for tables */
TAG_LPROTO, /* fixed tag for Lua functions */ TAG_LCLOSURE, /* fixed tag for Lua closures */
TAG_CPROTO, /* fixed tag for C functions */ TAG_CCLOSURE, /* fixed tag for C closures */
TAG_NIL, /* last "pre-defined" tag */ TAG_NIL, /* last "pre-defined" tag */
TAG_LCLOSURE, /* Lua closure */
TAG_CCLOSURE, /* C closure */
TAG_LCLMARK, /* mark for Lua closures */ TAG_LCLMARK, /* mark for Lua closures */
TAG_CCLMARK, /* mark for C closures */ TAG_CCLMARK, /* mark for C closures */
TAG_LMARK, /* mark for Lua prototypes */
TAG_CMARK, /* mark for C prototypes */
TAG_LINE TAG_LINE
} lua_Type; } lua_Type;
@ -58,20 +58,27 @@ typedef enum {
/* /*
** check whether `t' is a mark ** check whether `t' is a mark
*/ */
#define is_T_MARK(t) (TAG_LCLMARK <= (t) && (t) <= TAG_CMARK) #define is_T_MARK(t) ((t) == TAG_LCLMARK || (t) == TAG_CCLMARK)
typedef union { typedef union {
lua_CFunction f; /* TAG_CPROTO, TAG_CMARK */ struct TString *ts; /* TAG_STRING, TAG_USERDATA */
Number n; /* TAG_NUMBER */ struct Closure *cl; /* TAG_[CL]CLOSURE, TAG_[CL]CLMARK */
struct TString *ts; /* TAG_STRING, TAG_USERDATA */ struct Hash *a; /* TAG_TABLE */
struct Proto *tf; /* TAG_LPROTO, TAG_LMARK */ Number n; /* TAG_NUMBER */
struct Closure *cl; /* TAG_[CL]CLOSURE, TAG_[CL]CLMARK */ int i; /* TAG_LINE */
struct Hash *a; /* TAG_TABLE */
int i; /* TAG_LINE */
} Value; } Value;
/* Macros to access values */
#define ttype(o) ((o)->ttype)
#define nvalue(o) ((o)->value.n)
#define svalue(o) ((o)->value.ts->str)
#define tsvalue(o) ((o)->value.ts)
#define clvalue(o) ((o)->value.cl)
#define avalue(o) ((o)->value.a)
typedef struct TObject { typedef struct TObject {
lua_Type ttype; lua_Type ttype;
Value value; Value value;
@ -135,28 +142,18 @@ typedef struct LocVar {
} LocVar; } LocVar;
/* Macros to access structure members */
#define ttype(o) ((o)->ttype)
#define nvalue(o) ((o)->value.n)
#define svalue(o) ((o)->value.ts->str)
#define tsvalue(o) ((o)->value.ts)
#define clvalue(o) ((o)->value.cl)
#define avalue(o) ((o)->value.a)
#define fvalue(o) ((o)->value.f)
#define tfvalue(o) ((o)->value.tf)
#define protovalue(o) ((o)->value.cl->consts)
/* /*
** Closures ** Closures
*/ */
typedef struct Closure { typedef struct Closure {
struct Closure *next; struct Closure *next;
int marked; int marked;
int nelems; /* not including the first one (always the prototype) */ union {
TObject consts[1]; /* at least one for prototype */ lua_CFunction c; /* C functions */
struct Proto *l; /* Lua functions */
} f;
int nelems;
TObject consts[1];
} Closure; } Closure;

View File

@ -1,5 +1,5 @@
/* /*
** $Id: lparser.c,v 1.72 2000/03/24 12:17:53 roberto Exp roberto $ ** $Id: lparser.c,v 1.73 2000/03/24 17:26:08 roberto Exp roberto $
** LL(1) Parser and code generator for Lua ** LL(1) Parser and code generator for Lua
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -345,10 +345,6 @@ static void init_state (LexState *ls, FuncState *fs, TString *source) {
f->numparams = 0; /* default for main chunk */ f->numparams = 0; /* default for main chunk */
f->is_vararg = 0; /* default for main chunk */ f->is_vararg = 0; /* default for main chunk */
fs->nvars = (L->debug) ? 0 : -1; /* flag no debug information? */ fs->nvars = (L->debug) ? 0 : -1; /* flag no debug information? */
/* push function (to avoid GC) */
tfvalue(L->top) = f;
ttype(L->top) = TAG_LPROTO;
incr_top;
} }
@ -366,7 +362,6 @@ static void close_func (LexState *ls) {
luaM_reallocvector(L, f->locvars, fs->nvars, LocVar); luaM_reallocvector(L, f->locvars, fs->nvars, LocVar);
} }
ls->fs = fs->prev; ls->fs = fs->prev;
L->top--; /* pop function */
} }

6
lref.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: lref.c,v 1.9 2000/03/10 18:37:44 roberto Exp roberto $ ** $Id: lref.c,v 1.10 2000/03/27 20:10:21 roberto Exp roberto $
** reference mechanism ** reference mechanism
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -88,9 +88,7 @@ static int ismarked (const TObject *o) {
return o->value.a->marked; return o->value.a->marked;
case TAG_LCLOSURE: case TAG_CCLOSURE: case TAG_LCLOSURE: case TAG_CCLOSURE:
return o->value.cl->marked; return o->value.cl->marked;
case TAG_LPROTO: default: /* number */
return o->value.tf->marked;
default: /* number or cproto */
return 1; return 1;
} }
} }

View File

@ -1,5 +1,5 @@
/* /*
** $Id: ltable.c,v 1.36 2000/03/10 18:37:44 roberto Exp roberto $ ** $Id: ltable.c,v 1.37 2000/03/27 20:10:21 roberto Exp roberto $
** Lua tables (hash) ** Lua tables (hash)
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -52,12 +52,6 @@ Node *luaH_mainposition (const Hash *t, const TObject *key) {
case TAG_TABLE: case TAG_TABLE:
h = IntPoint(L, avalue(key)); h = IntPoint(L, avalue(key));
break; break;
case TAG_LPROTO:
h = IntPoint(L, tfvalue(key));
break;
case TAG_CPROTO:
h = IntPoint(L, fvalue(key));
break;
case TAG_LCLOSURE: case TAG_CCLOSURE: case TAG_LCLOSURE: case TAG_CCLOSURE:
h = IntPoint(L, clvalue(key)); h = IntPoint(L, clvalue(key));
break; break;

19
ltm.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: ltm.c,v 1.36 2000/03/27 20:08:02 roberto Exp roberto $ ** $Id: ltm.c,v 1.37 2000/03/27 20:10:21 roberto Exp roberto $
** Tag methods ** Tag methods
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -47,8 +47,8 @@ static const char luaT_validevents[NUM_TAGS][IM_N] = {
{1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1}, /* TAG_NUMBER */ {1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1}, /* TAG_NUMBER */
{1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1}, /* TAG_STRING */ {1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1}, /* TAG_STRING */
{0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1}, /* TAG_TABLE */ {0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1}, /* TAG_TABLE */
{1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0}, /* TAG_LPROTO */ {1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0}, /* TAG_LCLOSURE */
{1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0}, /* TAG_CPROTO */ {1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0}, /* TAG_CCLOSURE */
{1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1} /* TAG_NIL */ {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1} /* TAG_NIL */
}; };
@ -105,19 +105,14 @@ int lua_copytagmethods (lua_State *L, int tagto, int tagfrom) {
int luaT_effectivetag (lua_State *L, const TObject *o) { int luaT_effectivetag (lua_State *L, const TObject *o) {
static const int realtag[] = { /* ORDER LUA_T */ lua_Type t = ttype(o);
TAG_USERDATA, TAG_NUMBER, TAG_STRING, TAG_TABLE, switch (t) {
TAG_LPROTO, TAG_CPROTO, TAG_NIL,
TAG_LPROTO, TAG_CPROTO, /* TAG_LCLOSURE, TAG_CCLOSURE */
};
lua_Type t;
switch (t = ttype(o)) {
case TAG_USERDATA: { case TAG_USERDATA: {
int tag = o->value.ts->u.d.tag; int tag = o->value.ts->u.d.tag;
return (tag > L->last_tag) ? TAG_USERDATA : tag; /* deprecated test */ return (tag > L->last_tag) ? TAG_USERDATA : tag; /* deprecated test */
} }
case TAG_TABLE: return o->value.a->htag; case TAG_TABLE: return o->value.a->htag;
default: return realtag[t]; default: return t;
} }
} }

50
lvm.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: lvm.c,v 1.96 2000/03/17 13:09:12 roberto Exp roberto $ ** $Id: lvm.c,v 1.97 2000/03/27 20:10:21 roberto Exp roberto $
** Lua virtual machine ** Lua virtual machine
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -72,17 +72,27 @@ void luaV_setn (lua_State *L, Hash *t, int val) {
} }
void luaV_closure (lua_State *L, int nelems) { static Closure *luaV_closure (lua_State *L, lua_Type t, int nelems) {
if (nelems > 0) { Closure *c = luaF_newclosure(L, nelems);
Closure *c = luaF_newclosure(L, nelems); L->top -= nelems;
c->consts[0] = *(L->top-1); while (nelems--)
L->top -= nelems; c->consts[nelems] = *(L->top+nelems);
while (nelems--) ttype(L->top) = t;
c->consts[nelems+1] = *(L->top-1+nelems); clvalue(L->top) = c;
ttype(L->top-1) = (ttype(&c->consts[0]) == TAG_CPROTO) ? incr_top;
TAG_CCLOSURE : TAG_LCLOSURE; return c;
(L->top-1)->value.cl = c; }
}
void luaV_Cclosure (lua_State *L, lua_CFunction c, int nelems) {
Closure *cl = luaV_closure(L, TAG_CCLOSURE, nelems);
cl->f.c = c;
}
void luaV_Lclosure (lua_State *L, Proto *l, int nelems) {
Closure *cl = luaV_closure(L, TAG_LCLOSURE, nelems);
cl->f.l = l;
} }
@ -317,13 +327,11 @@ static void adjust_varargs (lua_State *L, StkId base, int nfixargs) {
** Executes the given Lua function. Parameters are between [base,top). ** Executes the given Lua function. Parameters are between [base,top).
** Returns n such that the the results are between [n,top). ** Returns n such that the the results are between [n,top).
*/ */
StkId luaV_execute (lua_State *L, const Closure *cl, const Proto *tf, StkId luaV_execute (lua_State *L, const Closure *cl, register StkId base) {
register StkId base) { const Proto *tf = cl->f.l;
register StkId top; /* keep top local, for performance */ register StkId top; /* keep top local, for performance */
register const Instruction *pc = tf->code; register const Instruction *pc = tf->code;
TString **kstr = tf->kstr; TString **kstr = tf->kstr;
if (L->callhook)
luaD_callHook(L, base-1, L->callhook, "call");
luaD_checkstack(L, tf->maxstacksize+EXTRA_STACK); luaD_checkstack(L, tf->maxstacksize+EXTRA_STACK);
if (tf->is_vararg) { /* varargs? */ if (tf->is_vararg) { /* varargs? */
adjust_varargs(L, base, tf->numparams); adjust_varargs(L, base, tf->numparams);
@ -392,7 +400,7 @@ StkId luaV_execute (lua_State *L, const Closure *cl, const Proto *tf,
break; break;
case OP_PUSHUPVALUE: case OP_PUSHUPVALUE:
*top++ = cl->consts[GETARG_U(i)+1]; *top++ = cl->consts[GETARG_U(i)];
break; break;
case OP_PUSHLOCAL: case OP_PUSHLOCAL:
@ -604,11 +612,9 @@ StkId luaV_execute (lua_State *L, const Closure *cl, const Proto *tf,
break; break;
case OP_CLOSURE: case OP_CLOSURE:
ttype(top) = TAG_LPROTO; L->top = top;
tfvalue(top) = tf->kproto[GETARG_A(i)]; luaV_Lclosure(L, tf->kproto[GETARG_A(i)], GETARG_B(i));
L->top = ++top; top = L->top;
luaV_closure(L, GETARG_B(i));
top -= GETARG_B(i);
luaC_checkGC(L); luaC_checkGC(L);
break; break;

7
lvm.h
View File

@ -1,5 +1,5 @@
/* /*
** $Id: lvm.h,v 1.18 2000/03/09 00:19:22 roberto Exp roberto $ ** $Id: lvm.h,v 1.19 2000/03/10 18:37:44 roberto Exp roberto $
** Lua virtual machine ** Lua virtual machine
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -26,8 +26,9 @@ void luaV_settable (lua_State *L, StkId t, StkId top);
void luaV_rawsettable (lua_State *L, StkId t); void luaV_rawsettable (lua_State *L, StkId t);
void luaV_getglobal (lua_State *L, GlobalVar *gv, StkId top); void luaV_getglobal (lua_State *L, GlobalVar *gv, StkId top);
void luaV_setglobal (lua_State *L, GlobalVar *gv, StkId top); void luaV_setglobal (lua_State *L, GlobalVar *gv, StkId top);
StkId luaV_execute (lua_State *L, const Closure *cl, const Proto *tf, StkId base); StkId luaV_execute (lua_State *L, const Closure *cl, register StkId base);
void luaV_closure (lua_State *L, int nelems); void luaV_Cclosure (lua_State *L, lua_CFunction c, int nelems);
void luaV_Lclosure (lua_State *L, Proto *l, int nelems);
int luaV_lessthan (lua_State *L, const TObject *l, const TObject *r, StkId top); int luaV_lessthan (lua_State *L, const TObject *l, const TObject *r, StkId top);
#endif #endif