diff options
Diffstat (limited to 'src/lua/lgc.c')
-rw-r--r-- | src/lua/lgc.c | 52 |
1 files changed, 29 insertions, 23 deletions
diff --git a/src/lua/lgc.c b/src/lua/lgc.c index 4a7bcae..5dba56f 100644 --- a/src/lua/lgc.c +++ b/src/lua/lgc.c | |||
@@ -161,18 +161,17 @@ static void linkgclist_ (GCObject *o, GCObject **pnext, GCObject **list) { | |||
161 | 161 | ||
162 | 162 | ||
163 | /* | 163 | /* |
164 | ** Clear keys for empty entries in tables. If entry is empty | 164 | ** Clear keys for empty entries in tables. If entry is empty, mark its |
165 | ** and its key is not marked, mark its entry as dead. This allows the | 165 | ** entry as dead. This allows the collection of the key, but keeps its |
166 | ** collection of the key, but keeps its entry in the table (its removal | 166 | ** entry in the table: its removal could break a chain and could break |
167 | ** could break a chain). The main feature of a dead key is that it must | 167 | ** a table traversal. Other places never manipulate dead keys, because |
168 | ** be different from any other value, to do not disturb searches. | 168 | ** its associated empty value is enough to signal that the entry is |
169 | ** Other places never manipulate dead keys, because its associated empty | 169 | ** logically empty. |
170 | ** value is enough to signal that the entry is logically empty. | ||
171 | */ | 170 | */ |
172 | static void clearkey (Node *n) { | 171 | static void clearkey (Node *n) { |
173 | lua_assert(isempty(gval(n))); | 172 | lua_assert(isempty(gval(n))); |
174 | if (keyiswhite(n)) | 173 | if (keyiscollectable(n)) |
175 | setdeadkey(n); /* unused and unmarked key; remove it */ | 174 | setdeadkey(n); /* unused key; remove it */ |
176 | } | 175 | } |
177 | 176 | ||
178 | 177 | ||
@@ -301,7 +300,7 @@ static void reallymarkobject (global_State *g, GCObject *o) { | |||
301 | if (upisopen(uv)) | 300 | if (upisopen(uv)) |
302 | set2gray(uv); /* open upvalues are kept gray */ | 301 | set2gray(uv); /* open upvalues are kept gray */ |
303 | else | 302 | else |
304 | set2black(o); /* closed upvalues are visited here */ | 303 | set2black(uv); /* closed upvalues are visited here */ |
305 | markvalue(g, uv->v); /* mark its content */ | 304 | markvalue(g, uv->v); /* mark its content */ |
306 | break; | 305 | break; |
307 | } | 306 | } |
@@ -309,7 +308,7 @@ static void reallymarkobject (global_State *g, GCObject *o) { | |||
309 | Udata *u = gco2u(o); | 308 | Udata *u = gco2u(o); |
310 | if (u->nuvalue == 0) { /* no user values? */ | 309 | if (u->nuvalue == 0) { /* no user values? */ |
311 | markobjectN(g, u->metatable); /* mark its metatable */ | 310 | markobjectN(g, u->metatable); /* mark its metatable */ |
312 | set2black(o); /* nothing else to mark */ | 311 | set2black(u); /* nothing else to mark */ |
313 | break; | 312 | break; |
314 | } | 313 | } |
315 | /* else... */ | 314 | /* else... */ |
@@ -633,8 +632,7 @@ static int traversethread (global_State *g, lua_State *th) { | |||
633 | for (uv = th->openupval; uv != NULL; uv = uv->u.open.next) | 632 | for (uv = th->openupval; uv != NULL; uv = uv->u.open.next) |
634 | markobject(g, uv); /* open upvalues cannot be collected */ | 633 | markobject(g, uv); /* open upvalues cannot be collected */ |
635 | if (g->gcstate == GCSatomic) { /* final traversal? */ | 634 | if (g->gcstate == GCSatomic) { /* final traversal? */ |
636 | StkId lim = th->stack + th->stacksize; /* real end of stack */ | 635 | for (; o < th->stack_last; o++) /* clear not-marked stack slice */ |
637 | for (; o < lim; o++) /* clear not-marked stack slice */ | ||
638 | setnilvalue(s2v(o)); | 636 | setnilvalue(s2v(o)); |
639 | /* 'remarkupvals' may have removed thread from 'twups' list */ | 637 | /* 'remarkupvals' may have removed thread from 'twups' list */ |
640 | if (!isintwups(th) && th->openupval != NULL) { | 638 | if (!isintwups(th) && th->openupval != NULL) { |
@@ -644,7 +642,7 @@ static int traversethread (global_State *g, lua_State *th) { | |||
644 | } | 642 | } |
645 | else if (!g->gcemergency) | 643 | else if (!g->gcemergency) |
646 | luaD_shrinkstack(th); /* do not change stack in emergency cycle */ | 644 | luaD_shrinkstack(th); /* do not change stack in emergency cycle */ |
647 | return 1 + th->stacksize; | 645 | return 1 + stacksize(th); |
648 | } | 646 | } |
649 | 647 | ||
650 | 648 | ||
@@ -771,12 +769,16 @@ static void freeobj (lua_State *L, GCObject *o) { | |||
771 | case LUA_VUPVAL: | 769 | case LUA_VUPVAL: |
772 | freeupval(L, gco2upv(o)); | 770 | freeupval(L, gco2upv(o)); |
773 | break; | 771 | break; |
774 | case LUA_VLCL: | 772 | case LUA_VLCL: { |
775 | luaM_freemem(L, o, sizeLclosure(gco2lcl(o)->nupvalues)); | 773 | LClosure *cl = gco2lcl(o); |
774 | luaM_freemem(L, cl, sizeLclosure(cl->nupvalues)); | ||
776 | break; | 775 | break; |
777 | case LUA_VCCL: | 776 | } |
778 | luaM_freemem(L, o, sizeCclosure(gco2ccl(o)->nupvalues)); | 777 | case LUA_VCCL: { |
778 | CClosure *cl = gco2ccl(o); | ||
779 | luaM_freemem(L, cl, sizeCclosure(cl->nupvalues)); | ||
779 | break; | 780 | break; |
781 | } | ||
780 | case LUA_VTABLE: | 782 | case LUA_VTABLE: |
781 | luaH_free(L, gco2t(o)); | 783 | luaH_free(L, gco2t(o)); |
782 | break; | 784 | break; |
@@ -788,13 +790,17 @@ static void freeobj (lua_State *L, GCObject *o) { | |||
788 | luaM_freemem(L, o, sizeudata(u->nuvalue, u->len)); | 790 | luaM_freemem(L, o, sizeudata(u->nuvalue, u->len)); |
789 | break; | 791 | break; |
790 | } | 792 | } |
791 | case LUA_VSHRSTR: | 793 | case LUA_VSHRSTR: { |
792 | luaS_remove(L, gco2ts(o)); /* remove it from hash table */ | 794 | TString *ts = gco2ts(o); |
793 | luaM_freemem(L, o, sizelstring(gco2ts(o)->shrlen)); | 795 | luaS_remove(L, ts); /* remove it from hash table */ |
796 | luaM_freemem(L, ts, sizelstring(ts->shrlen)); | ||
794 | break; | 797 | break; |
795 | case LUA_VLNGSTR: | 798 | } |
796 | luaM_freemem(L, o, sizelstring(gco2ts(o)->u.lnglen)); | 799 | case LUA_VLNGSTR: { |
800 | TString *ts = gco2ts(o); | ||
801 | luaM_freemem(L, ts, sizelstring(ts->u.lnglen)); | ||
797 | break; | 802 | break; |
803 | } | ||
798 | default: lua_assert(0); | 804 | default: lua_assert(0); |
799 | } | 805 | } |
800 | } | 806 | } |