diff options
| author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2003-07-29 16:25:37 -0300 |
|---|---|---|
| committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2003-07-29 16:25:37 -0300 |
| commit | a0a384a6b14b16bce8f48d2f2d327e716ae68f3d (patch) | |
| tree | 52980dbf3ade5c1259b8b2916555677c5eb9b8e7 | |
| parent | e89945aaa1f42cb41f401c44c56ed0c4a98004c6 (diff) | |
| download | lua-a0a384a6b14b16bce8f48d2f2d327e716ae68f3d.tar.gz lua-a0a384a6b14b16bce8f48d2f2d327e716ae68f3d.tar.bz2 lua-a0a384a6b14b16bce8f48d2f2d327e716ae68f3d.zip | |
bug: userdata to be collected still counts into new GC threshold,
increasing memory consumption
| -rw-r--r-- | lgc.c | 22 | ||||
| -rw-r--r-- | lgc.h | 4 |
2 files changed, 16 insertions, 10 deletions
| @@ -1,5 +1,5 @@ | |||
| 1 | /* | 1 | /* |
| 2 | ** $Id: lgc.c,v 1.174 2003/07/07 13:32:19 roberto Exp roberto $ | 2 | ** $Id: lgc.c,v 1.175 2003/07/16 20:49:02 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 | */ |
| @@ -108,7 +108,8 @@ static void marktmu (GCState *st) { | |||
| 108 | 108 | ||
| 109 | 109 | ||
| 110 | /* move `dead' udata that need finalization to list `tmudata' */ | 110 | /* move `dead' udata that need finalization to list `tmudata' */ |
| 111 | void luaC_separateudata (lua_State *L) { | 111 | size_t luaC_separateudata (lua_State *L) { |
| 112 | size_t deadmem = 0; | ||
| 112 | GCObject **p = &G(L)->rootudata; | 113 | GCObject **p = &G(L)->rootudata; |
| 113 | GCObject *curr; | 114 | GCObject *curr; |
| 114 | GCObject *collected = NULL; /* to collect udata with gc event */ | 115 | GCObject *collected = NULL; /* to collect udata with gc event */ |
| @@ -123,6 +124,7 @@ void luaC_separateudata (lua_State *L) { | |||
| 123 | p = &curr->gch.next; | 124 | p = &curr->gch.next; |
| 124 | } | 125 | } |
| 125 | else { /* must call its gc method */ | 126 | else { /* must call its gc method */ |
| 127 | deadmem += sizeudata(gcotou(curr)->uv.len); | ||
| 126 | markfinalized(gcotou(curr)); | 128 | markfinalized(gcotou(curr)); |
| 127 | *p = curr->gch.next; | 129 | *p = curr->gch.next; |
| 128 | curr->gch.next = NULL; /* link `curr' at the end of `collected' list */ | 130 | curr->gch.next = NULL; /* link `curr' at the end of `collected' list */ |
| @@ -133,6 +135,7 @@ void luaC_separateudata (lua_State *L) { | |||
| 133 | /* insert collected udata with gc event into `tmudata' list */ | 135 | /* insert collected udata with gc event into `tmudata' list */ |
| 134 | *lastcollected = G(L)->tmudata; | 136 | *lastcollected = G(L)->tmudata; |
| 135 | G(L)->tmudata = collected; | 137 | G(L)->tmudata = collected; |
| 138 | return deadmem; | ||
| 136 | } | 139 | } |
| 137 | 140 | ||
| 138 | 141 | ||
| @@ -377,7 +380,7 @@ static void sweepstrings (lua_State *L, int all) { | |||
| 377 | } | 380 | } |
| 378 | 381 | ||
| 379 | 382 | ||
| 380 | static void checkSizes (lua_State *L) { | 383 | static void checkSizes (lua_State *L, size_t deadmem) { |
| 381 | /* check size of string hash */ | 384 | /* check size of string hash */ |
| 382 | if (G(L)->strt.nuse < cast(lu_int32, G(L)->strt.size/4) && | 385 | if (G(L)->strt.nuse < cast(lu_int32, G(L)->strt.size/4) && |
| 383 | G(L)->strt.size > MINSTRTABSIZE*2) | 386 | G(L)->strt.size > MINSTRTABSIZE*2) |
| @@ -387,7 +390,8 @@ static void checkSizes (lua_State *L) { | |||
| 387 | size_t newsize = luaZ_sizebuffer(&G(L)->buff) / 2; | 390 | size_t newsize = luaZ_sizebuffer(&G(L)->buff) / 2; |
| 388 | luaZ_resizebuffer(L, &G(L)->buff, newsize); | 391 | luaZ_resizebuffer(L, &G(L)->buff, newsize); |
| 389 | } | 392 | } |
| 390 | G(L)->GCthreshold = 2*G(L)->nblocks; /* new threshold */ | 393 | lua_assert(G(L)->nblocks > deadmem); |
| 394 | G(L)->GCthreshold = 2*G(L)->nblocks - deadmem; /* new threshold */ | ||
| 391 | } | 395 | } |
| 392 | 396 | ||
| 393 | 397 | ||
| @@ -440,24 +444,26 @@ static void markroot (GCState *st, lua_State *L) { | |||
| 440 | } | 444 | } |
| 441 | 445 | ||
| 442 | 446 | ||
| 443 | static void mark (lua_State *L) { | 447 | static size_t mark (lua_State *L) { |
| 448 | size_t deadmem; | ||
| 444 | GCState st; | 449 | GCState st; |
| 445 | st.g = G(L); | 450 | st.g = G(L); |
| 446 | st.tmark = NULL; | 451 | st.tmark = NULL; |
| 447 | st.w = NULL; | 452 | st.w = NULL; |
| 448 | markroot(&st, L); | 453 | markroot(&st, L); |
| 449 | propagatemarks(&st); /* mark all reachable objects */ | 454 | propagatemarks(&st); /* mark all reachable objects */ |
| 450 | luaC_separateudata(L); /* separate userdata to be preserved */ | 455 | deadmem = luaC_separateudata(L); /* separate userdata to be preserved */ |
| 451 | marktmu(&st); /* mark `preserved' userdata */ | 456 | marktmu(&st); /* mark `preserved' userdata */ |
| 452 | propagatemarks(&st); /* remark, to propagate `preserveness' */ | 457 | propagatemarks(&st); /* remark, to propagate `preserveness' */ |
| 453 | cleartable(st.w); /* remove collected objects from weak tables */ | 458 | cleartable(st.w); /* remove collected objects from weak tables */ |
| 459 | return deadmem; | ||
| 454 | } | 460 | } |
| 455 | 461 | ||
| 456 | 462 | ||
| 457 | void luaC_collectgarbage (lua_State *L) { | 463 | void luaC_collectgarbage (lua_State *L) { |
| 458 | mark(L); | 464 | size_t deadmem = mark(L); |
| 459 | luaC_sweep(L, 0); | 465 | luaC_sweep(L, 0); |
| 460 | checkSizes(L); | 466 | checkSizes(L, deadmem); |
| 461 | luaC_callGCTM(L); | 467 | luaC_callGCTM(L); |
| 462 | } | 468 | } |
| 463 | 469 | ||
| @@ -1,5 +1,5 @@ | |||
| 1 | /* | 1 | /* |
| 2 | ** $Id: lgc.h,v 1.19 2003/02/28 19:45:15 roberto Exp $ | 2 | ** $Id: lgc.h,v 1.20 2003/07/16 20:49:02 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 | */ |
| @@ -15,7 +15,7 @@ | |||
| 15 | luaC_collectgarbage(L); } | 15 | luaC_collectgarbage(L); } |
| 16 | 16 | ||
| 17 | 17 | ||
| 18 | void luaC_separateudata (lua_State *L); | 18 | size_t luaC_separateudata (lua_State *L); |
| 19 | void luaC_callGCTM (lua_State *L); | 19 | void luaC_callGCTM (lua_State *L); |
| 20 | void luaC_sweep (lua_State *L, int all); | 20 | void luaC_sweep (lua_State *L, int all); |
| 21 | void luaC_collectgarbage (lua_State *L); | 21 | void luaC_collectgarbage (lua_State *L); |
