aboutsummaryrefslogtreecommitdiff
path: root/lgc.c
diff options
context:
space:
mode:
Diffstat (limited to 'lgc.c')
-rw-r--r--lgc.c64
1 files changed, 1 insertions, 63 deletions
diff --git a/lgc.c b/lgc.c
index 9d196a18..95a8ad5b 100644
--- a/lgc.c
+++ b/lgc.c
@@ -221,27 +221,6 @@ void luaC_barrierback_ (lua_State *L, GCObject *o) {
221} 221}
222 222
223 223
224/*
225** Barrier for prototype's cache of closures. It turns the prototype
226** back to gray (it was black). For an 'OLD1' prototype, making it
227** gray stops it from being visited by 'markold', so it is linked in
228** the 'grayagain' list to ensure it will be visited. For other ages,
229** it goes to the 'protogray' list, as only its 'cache' field needs to
230** be revisited. (A prototype to be in this barrier must be already
231** finished, so its other fields cannot change and do not need to be
232** revisited.)
233*/
234LUAI_FUNC void luaC_protobarrier_ (lua_State *L, Proto *p) {
235 global_State *g = G(L);
236 lua_assert(g->gckind != KGC_GEN || isold(p));
237 if (getage(p) == G_OLD1) /* still need to be visited? */
238 linkgclist(p, g->grayagain); /* link it in 'grayagain' */
239 else
240 linkgclist(p, g->protogray); /* link it in 'protogray' */
241 black2gray(p); /* make prototype gray */
242}
243
244
245void luaC_fix (lua_State *L, GCObject *o) { 224void luaC_fix (lua_State *L, GCObject *o) {
246 global_State *g = G(L); 225 global_State *g = G(L);
247 lua_assert(g->allgc == o); /* object must be 1st in 'allgc' list! */ 226 lua_assert(g->allgc == o); /* object must be 1st in 'allgc' list! */
@@ -379,7 +358,7 @@ static int remarkupvals (global_State *g) {
379*/ 358*/
380static void restartcollection (global_State *g) { 359static void restartcollection (global_State *g) {
381 g->gray = g->grayagain = NULL; 360 g->gray = g->grayagain = NULL;
382 g->weak = g->allweak = g->ephemeron = g->protogray = NULL; 361 g->weak = g->allweak = g->ephemeron = NULL;
383 markobject(g, g->mainthread); 362 markobject(g, g->mainthread);
384 markvalue(g, &g->l_registry); 363 markvalue(g, &g->l_registry);
385 markmt(g); 364 markmt(g);
@@ -535,39 +514,12 @@ static int traverseudata (global_State *g, Udata *u) {
535 514
536 515
537/* 516/*
538** Check the cache of a prototype, to keep invariants. If the
539** cache is white, clear it. (A cache should not prevent the
540** collection of its reference.) Otherwise, if in generational
541** mode, check the generational invariant. If the cache is old,
542** everything is ok. If the prototype is 'OLD0', everything
543** is ok too. (It will naturally be visited again.) If the
544** prototype is older than 'OLD0', then its cache (which is new)
545** must be visited again in the next collection, so the prototype
546** goes to the 'protogray' list. (If the prototype has a cache,
547** it is already immutable and does not need other barriers;
548** then, it can become gray without problems for its other fields.)
549*/
550static void checkprotocache (global_State *g, Proto *p) {
551 if (p->cache) {
552 if (iswhite(p->cache))
553 p->cache = NULL; /* allow cache to be collected */
554 else if (g->gckind == KGC_GEN && !isold(p->cache) && getage(p) >= G_OLD1) {
555 linkgclist(p, g->protogray); /* link it in 'protogray' */
556 black2gray(p); /* make prototype gray */
557 }
558 }
559 p->cachemiss = 0; /* restart counting */
560}
561
562
563/*
564** Traverse a prototype. (While a prototype is being build, its 517** Traverse a prototype. (While a prototype is being build, its
565** arrays can be larger than needed; the extra slots are filled with 518** arrays can be larger than needed; the extra slots are filled with
566** NULL, so the use of 'markobjectN') 519** NULL, so the use of 'markobjectN')
567*/ 520*/
568static int traverseproto (global_State *g, Proto *f) { 521static int traverseproto (global_State *g, Proto *f) {
569 int i; 522 int i;
570 checkprotocache(g, f);
571 markobjectN(g, f->source); 523 markobjectN(g, f->source);
572 for (i = 0; i < f->sizek; i++) /* mark literals */ 524 for (i = 0; i < f->sizek; i++) /* mark literals */
573 markvalue(g, &f->k[i]); 525 markvalue(g, &f->k[i]);
@@ -696,19 +648,6 @@ static void convergeephemerons (global_State *g) {
696** ======================================================= 648** =======================================================
697*/ 649*/
698 650
699static void clearprotolist (global_State *g) {
700 GCObject *p = g->protogray;
701 g->protogray = NULL;
702 while (p != NULL) {
703 Proto *pp = gco2p(p);
704 GCObject *next = pp->gclist;
705 lua_assert(isgray(pp) && (pp->cache != NULL || pp->cachemiss >= MAXMISS));
706 gray2black(pp);
707 checkprotocache(g, pp);
708 p = next;
709 }
710}
711
712 651
713/* 652/*
714** clear entries with unmarked keys from all weaktables in list 'l' 653** clear entries with unmarked keys from all weaktables in list 'l'
@@ -1439,7 +1378,6 @@ static lu_mem atomic (lua_State *L) {
1439 clearbyvalues(g, g->weak, origweak); 1378 clearbyvalues(g, g->weak, origweak);
1440 clearbyvalues(g, g->allweak, origall); 1379 clearbyvalues(g, g->allweak, origall);
1441 luaS_clearcache(g); 1380 luaS_clearcache(g);
1442 clearprotolist(g);
1443 g->currentwhite = cast_byte(otherwhite(g)); /* flip current white */ 1381 g->currentwhite = cast_byte(otherwhite(g)); /* flip current white */
1444 lua_assert(g->gray == NULL); 1382 lua_assert(g->gray == NULL);
1445 return work; /* estimate of slots marked by 'atomic' */ 1383 return work; /* estimate of slots marked by 'atomic' */