| 6158 | |
| 6159 | |
| 6160 | static int traversetable (global_State *g, Table *h) { |
| 6161 | int i; |
| 6162 | int weakkey = 0; |
| 6163 | int weakvalue = 0; |
| 6164 | const TValue *mode; |
| 6165 | if (h->metatable) |
| 6166 | markobject(g, h->metatable); |
| 6167 | mode = gfasttm(g, h->metatable, TM_MODE); |
| 6168 | if (mode && ttisstring(mode)) { /* is there a weak mode? */ |
| 6169 | weakkey = (strchr(svalue(mode), 'k') != NULL); |
| 6170 | weakvalue = (strchr(svalue(mode), 'v') != NULL); |
| 6171 | if (weakkey || weakvalue) { /* is really weak? */ |
| 6172 | h->marked &= ~(KEYWEAK | VALUEWEAK); /* clear bits */ |
| 6173 | h->marked |= cast_byte((weakkey << KEYWEAKBIT) | |
| 6174 | (weakvalue << VALUEWEAKBIT)); |
| 6175 | h->gclist = g->weak; /* must be cleared after GC, ... */ |
| 6176 | g->weak = obj2gco(h); /* ... so put in the appropriate list */ |
| 6177 | } |
| 6178 | } |
| 6179 | if (weakkey && weakvalue) return 1; |
| 6180 | if (!weakvalue) { |
| 6181 | i = h->sizearray; |
| 6182 | while (i--) |
| 6183 | markvalue(g, &h->array[i]); |
| 6184 | } |
| 6185 | i = sizenode(h); |
| 6186 | while (i--) { |
| 6187 | Node *n = gnode(h, i); |
| 6188 | lua_assert(ttype(gkey(n)) != LUA_TDEADKEY || ttisnil(gval(n))); |
| 6189 | if (ttisnil(gval(n))) |
| 6190 | removeentry(n); /* remove empty entries */ |
| 6191 | else { |
| 6192 | lua_assert(!ttisnil(gkey(n))); |
| 6193 | if (!weakkey) markvalue(g, gkey(n)); |
| 6194 | if (!weakvalue) markvalue(g, gval(n)); |
| 6195 | } |
| 6196 | } |
| 6197 | return weakkey || weakvalue; |
| 6198 | } |
| 6199 | |
| 6200 | |
| 6201 | /* |
no test coverage detected