Allow guardians to be GC'd before the objects they guard.
authorLudovic Courtes <ludovic.courtes@laas.fr>
Sun, 25 Jun 2006 22:43:05 +0000 (22:43 +0000)
committerLudovic Courtès <ludo@gnu.org>
Wed, 10 Sep 2008 18:27:54 +0000 (20:27 +0200)
* libguile/guardians.c (finalize_guarded): While traversing
  GUARDIANS_LIST, check for deleted weak-car pairs.
  (scm_i_guard): Instantiate GUARDIANS_FOR_OBJ using `scm_weak_car_pair ()'
  rather than `scm_cons ()'.

git-archimport-id: lcourtes@laas.fr--2005-libre/guile-core--boehm-gc--1.9--patch-41

libguile/guardians.c

index 649ed78..7ca11c4 100644 (file)
@@ -124,8 +124,13 @@ finalize_guarded (GC_PTR ptr, GC_PTR finalizer_data)
        guardian_list = SCM_CDR (guardian_list))
     {
       SCM zombies;
-      t_guardian *g = GUARDIAN_DATA (SCM_CAR (guardian_list));
+      t_guardian *g;
 
+      if (SCM_WEAK_PAIR_CAR_DELETED_P (guardian_list))
+       /* The guardian itself vanished in the meantime.  */
+       continue;
+
+      g = GUARDIAN_DATA (SCM_CAR (guardian_list));
       if (g->live == 0)
        abort ();
 
@@ -191,7 +196,10 @@ scm_i_guard (SCM guardian, SCM obj)
       SCM guardians_for_obj, finalizer_data;
 
       g->live++;
-      guardians_for_obj = scm_cons (guardian, SCM_EOL);
+
+      /* Note: GUARDIANS_FOR_OBJ is a weak list so that a guardian can be
+        collected before the objects it guards (see `guardians.test').  */
+      guardians_for_obj = scm_weak_car_pair (guardian, SCM_EOL);
       finalizer_data = scm_cons (SCM_BOOL_F, guardians_for_obj);
 
       GC_REGISTER_FINALIZER_NO_ORDER (SCM2PTR (obj), finalize_guarded,