fix garbage collector to handle multi-assigned variables and to not mess around
with cp_tr fields. git-svn-id: https://yap.svn.sf.net/svnroot/yap/trunk@1606 b08c6af1-5177-4d33-ba66-4b1c6b8b522a
This commit is contained in:
parent
9c12627e84
commit
9cbe63778e
104
C/heapgc.c
104
C/heapgc.c
@ -149,26 +149,17 @@ static rb_red_blk_node *db_root, *db_nil;
|
|||||||
static void
|
static void
|
||||||
gc_growtrail(int committed)
|
gc_growtrail(int committed)
|
||||||
{
|
{
|
||||||
#if !GC_TAGS
|
|
||||||
YAPLeaveCriticalSection();
|
|
||||||
#endif
|
|
||||||
#if USE_SYSTEM_MALLOC
|
#if USE_SYSTEM_MALLOC
|
||||||
TR = OldTR;
|
TR = OldTR;
|
||||||
#endif
|
save_machine_regs();
|
||||||
|
longjmp(Yap_gc_restore, 2);
|
||||||
|
#else
|
||||||
if (!Yap_growtrail(64 * 1024L, TRUE)) {
|
if (!Yap_growtrail(64 * 1024L, TRUE)) {
|
||||||
/* could not find more trail */
|
/* could not find more trail */
|
||||||
longjmp(Yap_gc_restore, 2);
|
|
||||||
}
|
|
||||||
#if USE_SYSTEM_MALLOC
|
|
||||||
#if !GC_NO_TAGS
|
|
||||||
if (committed) {
|
|
||||||
save_machine_regs();
|
save_machine_regs();
|
||||||
longjmp(Yap_gc_restore, 2);
|
longjmp(Yap_gc_restore, 2);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
save_machine_regs();
|
|
||||||
longjmp(Yap_gc_restore, 1);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1640,8 +1631,21 @@ mark_trail(tr_fr_ptr trail_ptr, tr_fr_ptr trail_base, CELL *gc_H, choiceptr gc_B
|
|||||||
value.
|
value.
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
if (cptr < (CELL *)gc_B && cptr >= gc_H) {
|
||||||
|
goto remove_trash_entry;
|
||||||
|
}
|
||||||
if (!gc_lookup_ma_var(cptr, trail_base)) {
|
if (!gc_lookup_ma_var(cptr, trail_base)) {
|
||||||
/* check whether this is the first time we see it*/
|
/* check whether this is the first time we see it*/
|
||||||
|
Term t0 = TrailTerm(trail_base+1);
|
||||||
|
|
||||||
|
if (!IsAtomicTerm(t0)) {
|
||||||
|
CELL *next = GET_NEXT(t0);
|
||||||
|
/* check if we have a garbage entry, where we are setting a
|
||||||
|
pointer to ourselves. */
|
||||||
|
if (next < (CELL *)gc_B && next >= gc_H) {
|
||||||
|
goto remove_trash_entry;
|
||||||
|
}
|
||||||
|
}
|
||||||
if (HEAP_PTR(trail_cell)) {
|
if (HEAP_PTR(trail_cell)) {
|
||||||
/* fool the gc into thinking this is a variable */
|
/* fool the gc into thinking this is a variable */
|
||||||
TrailTerm(trail_base) = (CELL)cptr;
|
TrailTerm(trail_base) = (CELL)cptr;
|
||||||
@ -1668,6 +1672,7 @@ mark_trail(tr_fr_ptr trail_ptr, tr_fr_ptr trail_base, CELL *gc_H, choiceptr gc_B
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
remove_trash_entry:
|
||||||
/* we can safely ignore this little monster */
|
/* we can safely ignore this little monster */
|
||||||
discard_trail_entries += 3;
|
discard_trail_entries += 3;
|
||||||
RESET_VARIABLE(&TrailTerm(trail_base));
|
RESET_VARIABLE(&TrailTerm(trail_base));
|
||||||
@ -1806,16 +1811,8 @@ mark_choicepoints(register choiceptr gc_B, tr_fr_ptr saved_TR, int very_verbose)
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
/* find out how many cells are still alive in the trail */
|
/* find out how many cells are still alive in the trail */
|
||||||
#ifndef FROZEN_STACKS
|
|
||||||
UInt d0 = discard_trail_entries, diff, orig;
|
|
||||||
orig = saved_TR-gc_B->cp_tr;
|
|
||||||
#endif
|
|
||||||
mark_trail(saved_TR, gc_B->cp_tr, gc_B->cp_h, gc_B);
|
mark_trail(saved_TR, gc_B->cp_tr, gc_B->cp_h, gc_B);
|
||||||
saved_TR = gc_B->cp_tr;
|
saved_TR = gc_B->cp_tr;
|
||||||
#ifndef FROZEN_STACKS
|
|
||||||
diff = discard_trail_entries-d0;
|
|
||||||
gc_B->cp_tr = (tr_fr_ptr)(orig-diff);
|
|
||||||
#endif /* FROZEN_STACKS */
|
|
||||||
}
|
}
|
||||||
if (opnum == _or_else || opnum == _or_last) {
|
if (opnum == _or_else || opnum == _or_last) {
|
||||||
/* ; choice point */
|
/* ; choice point */
|
||||||
@ -2191,17 +2188,44 @@ sweep_trail(choiceptr gc_B, tr_fr_ptr old_TR)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifndef FROZEN_STACKS
|
#ifndef FROZEN_STACKS
|
||||||
/*
|
|
||||||
adjust cp_tr pointers,
|
|
||||||
we don't compress TR if we have freeze.
|
|
||||||
*/
|
|
||||||
{
|
{
|
||||||
Int size = old_TR-(tr_fr_ptr)Yap_TrailBase;
|
choiceptr current = gc_B;
|
||||||
size -= discard_trail_entries;
|
choiceptr next = gc_B->cp_b;
|
||||||
while (gc_B != NULL) {
|
tr_fr_ptr source, dest;
|
||||||
size -= (UInt)(gc_B->cp_tr);
|
|
||||||
gc_B->cp_tr = (tr_fr_ptr)Yap_TrailBase+size;
|
/* invert cp ptrs */
|
||||||
gc_B = gc_B->cp_b;
|
current->cp_b = NULL;
|
||||||
|
while (next) {
|
||||||
|
choiceptr n = next;
|
||||||
|
next = n->cp_b;
|
||||||
|
n->cp_b = current;
|
||||||
|
current = n;
|
||||||
|
}
|
||||||
|
|
||||||
|
next = current;
|
||||||
|
current = NULL;
|
||||||
|
/* next, clean trail */
|
||||||
|
source = dest = (tr_fr_ptr)Yap_TrailBase;
|
||||||
|
while (source < old_TR) {
|
||||||
|
while (next && source == next->cp_tr) {
|
||||||
|
choiceptr b = next;
|
||||||
|
b->cp_tr = dest;
|
||||||
|
next = b->cp_b;
|
||||||
|
b->cp_b = current;
|
||||||
|
current = b;
|
||||||
|
}
|
||||||
|
CELL trail_cell = TrailTerm(source);
|
||||||
|
if (trail_cell != (CELL)source) {
|
||||||
|
dest++;
|
||||||
|
}
|
||||||
|
source++;
|
||||||
|
}
|
||||||
|
while (next) {
|
||||||
|
choiceptr b = next;
|
||||||
|
b->cp_tr = dest;
|
||||||
|
next = b->cp_b;
|
||||||
|
b->cp_b = current;
|
||||||
|
current = b;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif /* FROZEN_STACKS */
|
#endif /* FROZEN_STACKS */
|
||||||
@ -3398,23 +3422,23 @@ marking_phase(tr_fr_ptr old_TR, CELL *current_env, yamop *curp, CELL *max)
|
|||||||
|
|
||||||
#ifdef EASY_SHUNTING
|
#ifdef EASY_SHUNTING
|
||||||
current_B = B;
|
current_B = B;
|
||||||
|
prev_HB = H;
|
||||||
#endif
|
#endif
|
||||||
init_dbtable(old_TR);
|
init_dbtable(old_TR);
|
||||||
#ifdef EASY_SHUNTING
|
#ifdef EASY_SHUNTING
|
||||||
sTR0 = (tr_fr_ptr)db_vec;
|
sTR0 = (tr_fr_ptr)db_vec;
|
||||||
sTR = (tr_fr_ptr)db_vec;
|
sTR = (tr_fr_ptr)db_vec;
|
||||||
/* make sure we set HB before we do any variable shunting!!! */
|
/* make sure we set HB before we do any variable shunting!!! */
|
||||||
HB = H;
|
|
||||||
#else
|
#else
|
||||||
cont_top0 = (cont *)db_vec;
|
cont_top0 = (cont *)db_vec;
|
||||||
#endif
|
#endif
|
||||||
cont_top = (cont *)db_vec;
|
cont_top = (cont *)db_vec;
|
||||||
/* These two must be marked first so that our trail optimisation won't lose
|
|
||||||
values */
|
|
||||||
mark_regs(old_TR); /* active registers & trail */
|
|
||||||
#ifdef COROUTINING
|
#ifdef COROUTINING
|
||||||
mark_delays(max);
|
mark_delays(max);
|
||||||
#endif
|
#endif
|
||||||
|
/* These two must be marked first so that our trail optimisation won't lose
|
||||||
|
values */
|
||||||
|
mark_regs(old_TR); /* active registers & trail */
|
||||||
/* active environments */
|
/* active environments */
|
||||||
mark_environments(current_env, EnvSize(curp), EnvBMap((CELL *)curp));
|
mark_environments(current_env, EnvSize(curp), EnvBMap((CELL *)curp));
|
||||||
mark_choicepoints(B, old_TR, is_gc_very_verbose()); /* choicepoints, and environs */
|
mark_choicepoints(B, old_TR, is_gc_very_verbose()); /* choicepoints, and environs */
|
||||||
@ -3665,6 +3689,12 @@ do_gc(Int predarity, CELL *current_env, yamop *nextop)
|
|||||||
return 0;
|
return 0;
|
||||||
#endif
|
#endif
|
||||||
} else {
|
} else {
|
||||||
|
total_marked = 0;
|
||||||
|
total_oldies = 0;
|
||||||
|
#ifdef COROUTING
|
||||||
|
total_smarked = 0;
|
||||||
|
#endif
|
||||||
|
discard_trail_entries = 0;
|
||||||
current_env = (CELL *)*ASP;
|
current_env = (CELL *)*ASP;
|
||||||
ASP++;
|
ASP++;
|
||||||
#if COROUTINING
|
#if COROUTINING
|
||||||
@ -3683,9 +3713,6 @@ do_gc(Int predarity, CELL *current_env, yamop *nextop)
|
|||||||
HGEN = H0;
|
HGEN = H0;
|
||||||
}
|
}
|
||||||
/* fprintf(stderr,"HGEN is %ld, %p, %p/%p\n", IntegerOfTerm(Yap_ReadTimedVar(GcGeneration)), HGEN, H,H0);*/
|
/* fprintf(stderr,"HGEN is %ld, %p, %p/%p\n", IntegerOfTerm(Yap_ReadTimedVar(GcGeneration)), HGEN, H,H0);*/
|
||||||
#if !GC_TAGS
|
|
||||||
YAPEnterCriticalSection();
|
|
||||||
#endif
|
|
||||||
OldTR = (tr_fr_ptr)(old_TR = TR);
|
OldTR = (tr_fr_ptr)(old_TR = TR);
|
||||||
push_registers(predarity, nextop);
|
push_registers(predarity, nextop);
|
||||||
marking_phase(old_TR, current_env, nextop, max);
|
marking_phase(old_TR, current_env, nextop, max);
|
||||||
@ -3732,9 +3759,6 @@ do_gc(Int predarity, CELL *current_env, yamop *nextop)
|
|||||||
TR = old_TR;
|
TR = old_TR;
|
||||||
pop_registers(predarity, nextop);
|
pop_registers(predarity, nextop);
|
||||||
TR = new_TR;
|
TR = new_TR;
|
||||||
#if !GC_TAGS
|
|
||||||
YAPLeaveCriticalSection();
|
|
||||||
#endif
|
|
||||||
/* fprintf(Yap_stderr,"NEW HGEN %ld (%ld)\n", H-H0, HGEN-H0);*/
|
/* fprintf(Yap_stderr,"NEW HGEN %ld (%ld)\n", H-H0, HGEN-H0);*/
|
||||||
Yap_UpdateTimedVar(GcGeneration, MkIntegerTerm(H-H0));
|
Yap_UpdateTimedVar(GcGeneration, MkIntegerTerm(H-H0));
|
||||||
Yap_UpdateTimedVar(GcPhase, MkIntegerTerm(GcCurrentPhase));
|
Yap_UpdateTimedVar(GcPhase, MkIntegerTerm(GcCurrentPhase));
|
||||||
|
@ -137,6 +137,10 @@ low_level_trace(yap_low_level_port port, PredEntry *pred, CELL *args)
|
|||||||
LOCK(Yap_heap_regs->low_level_trace_lock);
|
LOCK(Yap_heap_regs->low_level_trace_lock);
|
||||||
sc = Yap_heap_regs;
|
sc = Yap_heap_regs;
|
||||||
vsc_count++;
|
vsc_count++;
|
||||||
|
// if (vsc_count < 13600) {
|
||||||
|
// UNLOCK(Yap_heap_regs->low_level_trace_lock);
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
#ifdef COMMENTED
|
#ifdef COMMENTED
|
||||||
// if (vsc_count == 218280)
|
// if (vsc_count == 218280)
|
||||||
// vsc_xstop = 1;
|
// vsc_xstop = 1;
|
||||||
|
@ -16,6 +16,11 @@
|
|||||||
|
|
||||||
<h2>Yap-5.1.2:</h2>
|
<h2>Yap-5.1.2:</h2>
|
||||||
<ul>
|
<ul>
|
||||||
|
<li> FIXED: garbage collector should no rewrite cp_tr fields until
|
||||||
|
after marking (obs Paulo Moura).</li>
|
||||||
|
<li> FIXED: garbage collector was allowing garbage trail entries for
|
||||||
|
multi-assignment variables. Namely, old var value might point to new space
|
||||||
|
(obs Paulo Moura).</li>
|
||||||
<li> FIXED: thread aliases were being cleaned up just after being
|
<li> FIXED: thread aliases were being cleaned up just after being
|
||||||
installed (obs Paulo Moura).</li>
|
installed (obs Paulo Moura).</li>
|
||||||
<li> FIXED: rb_partial_map was broken.</li>
|
<li> FIXED: rb_partial_map was broken.</li>
|
||||||
|
Reference in New Issue
Block a user