diff options
author | Simon Marlow <marlowsd@gmail.com> | 2009-12-08 09:48:22 +0000 |
---|---|---|
committer | Simon Marlow <marlowsd@gmail.com> | 2009-12-08 09:48:22 +0000 |
commit | 852154bd9501f491b5499013e90922686850c833 (patch) | |
tree | b0c3b29ceb0a241a9d57ba569a58d5787bbe82a2 /rts/sm/MarkWeak.c | |
parent | 4207605cc8e035e05f651334ef1be90b098d305d (diff) | |
download | haskell-852154bd9501f491b5499013e90922686850c833.tar.gz |
simplify weak pointer processing
Diffstat (limited to 'rts/sm/MarkWeak.c')
-rw-r--r-- | rts/sm/MarkWeak.c | 37 |
1 files changed, 15 insertions, 22 deletions
diff --git a/rts/sm/MarkWeak.c b/rts/sm/MarkWeak.c index 9d8e8c01a9..7b7187c94d 100644 --- a/rts/sm/MarkWeak.c +++ b/rts/sm/MarkWeak.c @@ -127,14 +127,8 @@ traverseWeakPtrList(void) continue; } - info = w->header.info; - if (IS_FORWARDING_PTR(info)) { - next_w = (StgWeak *)UN_FORWARDING_PTR(info); - *last_w = next_w; - continue; - } - - switch (INFO_PTR_TO_STRUCT(info)->type) { + info = get_itbl(w); + switch (info->type) { case WEAK: /* Now, check whether the key is reachable. @@ -386,21 +380,17 @@ traverseBlackholeQueue (void) } /* ----------------------------------------------------------------------------- - After GC, the live weak pointer list may have forwarding pointers - on it, because a weak pointer object was evacuated after being - moved to the live weak pointer list. We remove those forwarding - pointers here. - - Also, we don't consider weak pointer objects to be reachable, but - we must nevertheless consider them to be "live" and retain them. - Therefore any weak pointer objects which haven't as yet been - evacuated need to be evacuated now. + Evacuate every weak pointer object on the weak_ptr_list, and update + the link fields. + + ToDo: with a lot of weak pointers, this will be expensive. We + should have a per-GC weak pointer list, just like threads. -------------------------------------------------------------------------- */ void markWeakPtrList ( void ) { - StgWeak *w, **last_w, *tmp; + StgWeak *w, **last_w; last_w = &weak_ptr_list; for (w = weak_ptr_list; w; w = w->link) { @@ -408,10 +398,13 @@ markWeakPtrList ( void ) ASSERT(IS_FORWARDING_PTR(w->header.info) || w->header.info == &stg_DEAD_WEAK_info || get_itbl(w)->type == WEAK); - tmp = w; - evacuate((StgClosure **)&tmp); - *last_w = w; - last_w = &(w->link); + evacuate((StgClosure **)last_w); + w = *last_w; + if (w->header.info == &stg_DEAD_WEAK_info) { + last_w = &(((StgDeadWeak*)w)->link); + } else { + last_w = &(w->link); + } } } |