aboutsummaryrefslogtreecommitdiff
path: root/lgc.c
diff options
context:
space:
mode:
Diffstat (limited to 'lgc.c')
-rw-r--r--lgc.c40
1 files changed, 26 insertions, 14 deletions
diff --git a/lgc.c b/lgc.c
index 0c84da8f..189adc6a 100644
--- a/lgc.c
+++ b/lgc.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lgc.c,v 1.78 2001/01/22 18:01:38 roberto Exp roberto $ 2** $Id: lgc.c,v 1.79 2001/01/25 16:45:36 roberto Exp roberto $
3** Garbage Collector 3** Garbage Collector
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -121,6 +121,29 @@ static void marktagmethods (global_State *G, GCState *st) {
121} 121}
122 122
123 123
124static void traverseclosure (GCState *st, Closure *f) {
125 int i;
126 for (i=0; i<f->nupvalues; i++) /* mark its upvalues */
127 markobject(st, &f->upvalue[i]);
128}
129
130
131static void traversetable (GCState *st, Hash *h) {
132 int i;
133 for (i=0; i<h->size; i++) {
134 Node *n = node(h, i);
135 if (ttype(val(n)) == LUA_TNIL) {
136 if (ttype(key(n)) != LUA_TNIL)
137 sethvalue(key(n), NULL); /* dead key; remove it */
138 }
139 else {
140 markobject(st, &n->key);
141 markobject(st, &n->val);
142 }
143 }
144}
145
146
124static void markall (lua_State *L) { 147static void markall (lua_State *L) {
125 GCState st; 148 GCState st;
126 st.cmark = NULL; 149 st.cmark = NULL;
@@ -131,25 +154,14 @@ static void markall (lua_State *L) {
131 marktable(&st, G(L)->type2tag); 154 marktable(&st, G(L)->type2tag);
132 for (;;) { /* mark tables and closures */ 155 for (;;) { /* mark tables and closures */
133 if (st.cmark) { 156 if (st.cmark) {
134 int i;
135 Closure *f = st.cmark; /* get first closure from list */ 157 Closure *f = st.cmark; /* get first closure from list */
136 st.cmark = f->mark; /* remove it from list */ 158 st.cmark = f->mark; /* remove it from list */
137 for (i=0; i<f->nupvalues; i++) /* mark its upvalues */ 159 traverseclosure(&st, f);
138 markobject(&st, &f->upvalue[i]);
139 } 160 }
140 else if (st.tmark) { 161 else if (st.tmark) {
141 int i;
142 Hash *h = st.tmark; /* get first table from list */ 162 Hash *h = st.tmark; /* get first table from list */
143 st.tmark = h->mark; /* remove it from list */ 163 st.tmark = h->mark; /* remove it from list */
144 for (i=0; i<h->size; i++) { 164 traversetable(&st, h);
145 Node *n = node(h, i);
146 if (ttype(key(n)) != LUA_TNIL) {
147 if (ttype(val(n)) == LUA_TNIL)
148 luaH_remove(h, key(n)); /* dead element; try to remove it */
149 markobject(&st, &n->key);
150 markobject(&st, &n->val);
151 }
152 }
153 } 165 }
154 else break; /* nothing else to mark */ 166 else break; /* nothing else to mark */
155 } 167 }