diff options
Diffstat (limited to 'src/lstate.h')
-rw-r--r-- | src/lstate.h | 114 |
1 files changed, 82 insertions, 32 deletions
diff --git a/src/lstate.h b/src/lstate.h index 3bc575b6..4ca3e02f 100644 --- a/src/lstate.h +++ b/src/lstate.h @@ -1,5 +1,5 @@ /* -** $Id: lstate.h,v 2.24.1.2 2008/01/03 15:20:39 roberto Exp $ +** $Id: lstate.h,v 2.52 2009/12/22 15:32:50 roberto Exp $ ** Global State ** See Copyright Notice in lua.h */ @@ -14,15 +14,35 @@ #include "lzio.h" +/* -struct lua_longjmp; /* defined in ldo.c */ +** Some notes about garbage-collected objects: All objects in Lua must +** be kept somehow accessible until being freed. +** +** Lua keeps most objects linked in list g->rootgc. The link uses field +** 'next' of the CommonHeader. +** +** Strings are kept in several lists headed by the array g->strt.hash. +** +** Open upvalues are not subject to independent garbage collection. They +** are collected together with their respective threads. Lua keeps a +** double-linked list with all open upvalues (g->uvhead) so that it can +** mark objects referred by them. (They are always gray, so they must +** be remarked in the atomic step. Usually their contents would be marked +** when traversing the respective threads, but the thread may already be +** dead, while the upvalue is still accessible through closures.) +** +** Userdata with finalizers are kept in the list g->rootgc, but after +** the mainthread, which should be otherwise the last element in the +** list, as it was the first one inserted there. +** +** The list g->tobefnz links all userdata being finalized. +*/ -/* table of globals */ -#define gt(L) (&L->l_gt) -/* registry */ -#define registry(L) (&G(L)->l_registry) +struct lua_longjmp; /* defined in ldo.c */ + /* extra stack space to handle TM calls and some other extras */ @@ -34,6 +54,11 @@ struct lua_longjmp; /* defined in ldo.c */ #define BASIC_STACK_SIZE (2*LUA_MINSTACK) +/* kinds of Garbage Collection */ +#define KGC_NORMAL 0 +#define KGC_FORCED 1 /* gc was forced by the program */ +#define KGC_EMERGENCY 2 /* gc was forced by an allocation failure */ + typedef struct stringtable { GCObject **hash; @@ -46,20 +71,44 @@ typedef struct stringtable { ** informations about a call */ typedef struct CallInfo { - StkId base; /* base for this function */ StkId func; /* function index in the stack */ StkId top; /* top for this function */ - const Instruction *savedpc; - int nresults; /* expected number of results from this function */ - int tailcalls; /* number of tail calls lost under this entry */ + struct CallInfo *previous, *next; /* dynamic call link */ + short nresults; /* expected number of results from a call */ + lu_byte callstatus; + union { + struct { /* only for Lua functions */ + StkId base; /* base for this function */ + const Instruction *savedpc; + } l; + struct { /* only for C functions */ + int ctx; /* context info. in case of yields */ + lua_CFunction k; /* continuation in case of yields */ + ptrdiff_t old_errfunc; + ptrdiff_t oldtop; + lu_byte old_allowhook; + lu_byte status; + } c; + } u; } CallInfo; +/* +** Bits in CallInfo status +*/ +#define CIST_LUA (1<<0) /* call is running a Lua function */ +#define CIST_HOOKED (1<<1) /* call is running a debug hook */ +#define CIST_REENTRY (1<<2) /* call is running on same invocation of + luaV_execute of previous call */ +#define CIST_YIELDED (1<<3) /* call reentered after suspension */ +#define CIST_YPCALL (1<<4) /* call is a yieldable protected call */ +#define CIST_STAT (1<<5) /* call has an error status (pcall) */ +#define CIST_TAIL (1<<6) /* call was tail called */ + #define curr_func(L) (clvalue(L->ci->func)) #define ci_func(ci) (clvalue((ci)->func)) -#define f_isLua(ci) (!ci_func(ci)->c.isC) -#define isLua(ci) (ttisfunction((ci)->func) && f_isLua(ci)) +#define isLua(ci) ((ci)->callstatus & CIST_LUA) /* @@ -69,26 +118,30 @@ typedef struct global_State { stringtable strt; /* hash table for strings */ lua_Alloc frealloc; /* function to reallocate memory */ void *ud; /* auxiliary data to `frealloc' */ + unsigned short nCcalls; /* number of nested C calls */ lu_byte currentwhite; lu_byte gcstate; /* state of garbage collector */ + lu_byte gckind; /* kind of GC running */ int sweepstrgc; /* position of sweep in `strt' */ GCObject *rootgc; /* list of all collectable objects */ - GCObject **sweepgc; /* position of sweep in `rootgc' */ + GCObject **sweepgc; /* current position of sweep */ GCObject *gray; /* list of gray objects */ GCObject *grayagain; /* list of objects to be traversed atomically */ - GCObject *weak; /* list of weak tables (to be cleared) */ - GCObject *tmudata; /* last element of list of userdata to be GC */ - Mbuffer buff; /* temporary buffer for string concatentation */ - lu_mem GCthreshold; + GCObject *weak; /* list of tables with weak values */ + GCObject *ephemeron; /* list of ephemeron tables (weak keys) */ + GCObject *allweak; /* list of all-weak tables */ + GCObject *tobefnz; /* list of userdata to be GC */ + Mbuffer buff; /* temporary buffer for string concatenation */ + lu_mem GCthreshold; /* when totalbytes > GCthreshold, run GC step */ lu_mem totalbytes; /* number of bytes currently allocated */ - lu_mem estimate; /* an estimate of number of bytes actually in use */ - lu_mem gcdept; /* how much GC is `behind schedule' */ int gcpause; /* size of pause between successive GCs */ int gcstepmul; /* GC `granularity' */ lua_CFunction panic; /* to be called in unprotected errors */ TValue l_registry; + struct Table *l_gt; /* table of globals */ struct lua_State *mainthread; UpVal uvhead; /* head of double-linked list of all open upvalues */ + const lua_Number *version; /* pointer to version number */ struct Table *mt[NUM_TAGS]; /* metatables for basic types */ TString *tmname[TM_N]; /* array with tag-method names */ } global_State; @@ -101,29 +154,24 @@ struct lua_State { CommonHeader; lu_byte status; StkId top; /* first free slot in the stack */ - StkId base; /* base of current function */ global_State *l_G; CallInfo *ci; /* call info for current function */ - const Instruction *savedpc; /* `savedpc' of current function */ + const Instruction *oldpc; /* last pc traced */ StkId stack_last; /* last free slot in the stack */ StkId stack; /* stack base */ - CallInfo *end_ci; /* points after end of ci array*/ - CallInfo *base_ci; /* array of CallInfo's */ int stacksize; - int size_ci; /* size of array `base_ci' */ - unsigned short nCcalls; /* number of nested C calls */ - unsigned short baseCcalls; /* nested C calls when resuming coroutine */ + unsigned short nny; /* number of non-yieldable calls in stack */ lu_byte hookmask; lu_byte allowhook; int basehookcount; int hookcount; lua_Hook hook; - TValue l_gt; /* table of globals */ TValue env; /* temporary place for environments */ GCObject *openupval; /* list of open upvalues in this stack */ GCObject *gclist; struct lua_longjmp *errorJmp; /* current error recover point */ ptrdiff_t errfunc; /* current error handling function (stack index) */ + CallInfo base_ci; /* CallInfo for first level (C calling Lua) */ }; @@ -134,7 +182,7 @@ struct lua_State { ** Union of all collectable objects */ union GCObject { - GCheader gch; + GCheader gch; /* common header */ union TString ts; union Udata u; union Closure cl; @@ -145,25 +193,27 @@ union GCObject { }; +#define gch(o) (&(o)->gch) + /* macros to convert a GCObject into a specific value */ #define rawgco2ts(o) check_exp((o)->gch.tt == LUA_TSTRING, &((o)->ts)) #define gco2ts(o) (&rawgco2ts(o)->tsv) #define rawgco2u(o) check_exp((o)->gch.tt == LUA_TUSERDATA, &((o)->u)) #define gco2u(o) (&rawgco2u(o)->uv) #define gco2cl(o) check_exp((o)->gch.tt == LUA_TFUNCTION, &((o)->cl)) -#define gco2h(o) check_exp((o)->gch.tt == LUA_TTABLE, &((o)->h)) +#define gco2t(o) check_exp((o)->gch.tt == LUA_TTABLE, &((o)->h)) #define gco2p(o) check_exp((o)->gch.tt == LUA_TPROTO, &((o)->p)) #define gco2uv(o) check_exp((o)->gch.tt == LUA_TUPVAL, &((o)->uv)) -#define ngcotouv(o) \ - check_exp((o) == NULL || (o)->gch.tt == LUA_TUPVAL, &((o)->uv)) #define gco2th(o) check_exp((o)->gch.tt == LUA_TTHREAD, &((o)->th)) /* macro to convert any Lua object into a GCObject */ #define obj2gco(v) (cast(GCObject *, (v))) -LUAI_FUNC lua_State *luaE_newthread (lua_State *L); LUAI_FUNC void luaE_freethread (lua_State *L, lua_State *L1); +LUAI_FUNC CallInfo *luaE_extendCI (lua_State *L); +LUAI_FUNC void luaE_freeCI (lua_State *L); + #endif |