]> granicus.if.org Git - gc/commitdiff
Add GC_reachable_here after GC_END_STUBBORN_CHANGE in tests
authorIvan Maidanski <ivmai@mail.ru>
Thu, 21 Jun 2018 21:57:09 +0000 (00:57 +0300)
committerIvan Maidanski <ivmai@mail.ru>
Thu, 21 Jun 2018 21:57:09 +0000 (00:57 +0300)
(fix of commits b52c140d3f72fc9d4308a380c3a)

* tests/disclaim_test.c (pair_dct, pair_new): Call GC_reachable_here
for the stored pointers after GC_end_stubborn_change call.
* tests/staticrootslib.c (libsrl_mktree): Call GC_reachable_here for
the stored pointers after GC_END_STUBBORN_CHANGE call.
* tests/test.c (cons, small_cons, small_cons_uncollectable, mktree,
typed_test): Likewise.
* tests/test.c [GC_GCJ_SUPPORT] (gcj_cons): Likewise.
* tests/test.c [!SMALL_CONFIG && !GC_DEBUG] (alloc8bytes): Likewise.
* tests/test_cpp.cc [!DONT_USE_STD_ALLOCATOR] (main): Likewise.
* tests/trace_test.c (mktree): Likewise.
* tests/test.c (reverse_test_inner): Declare tmp local variable; call
GC_END_STUBBORN_CHANGE() and GC_reachable_here() after storing pointers
to f[5], g[799] and h[1999].
* tests/test_cpp.cc (C_INIT_LEFT_RIGHT): New macro (to call
GC_END_STUBBORN_CHANGE and GC_reachable_here).
* tests/test_cpp.cc (C::C): Use C_INIT_LEFT_RIGHT().
* tests/test_cpp.cc (main): Remove GC_end_stubborn_change(c) call after
because GC_END_STUBBORN_CHANGE() is now called for this (in
C_INIT_LEFT_RIGHT) of the heap-allocated objects.

tests/disclaim_test.c
tests/staticrootslib.c
tests/test.c
tests/test_cpp.cc
tests/trace_test.c

index 8cfb53990ed8de630b7e66623d9773d0e0f3f9eb..0a67892c91174626653b0113c0a68ae9c31ebd31 100644 (file)
@@ -129,6 +129,7 @@ void GC_CALLBACK pair_dct(void *obj, void *cd)
     p->car = (pair_t)cd;
     p->cdr = NULL;
     GC_end_stubborn_change(p);
+    GC_reachable_here(cd);
 }
 
 pair_t
@@ -149,6 +150,8 @@ pair_new(pair_t car, pair_t cdr)
     p->car = car;
     p->cdr = cdr;
     GC_end_stubborn_change(p);
+    GC_reachable_here(car);
+    GC_reachable_here(cdr);
 #   ifdef DEBUG_DISCLAIM_DESTRUCT
       printf("Construct %p = (%p, %p)\n",
              (void *)p, (void *)p->car, (void *)p->cdr);
index a445a095a69b46fabf147de235d50c320a13987b..c7c0725a959bc34c234d62e05192866d0b67212e 100644 (file)
@@ -37,10 +37,15 @@ static struct treenode *root_nz[10] = { (struct treenode *)(GC_word)2 };
     if (1 == i)
       r = (struct treenode *)GC_MALLOC_ATOMIC(sizeof(struct treenode));
     if (r) {
-      r -> x = libsrl_mktree(i-1);
-      r -> y = libsrl_mktree(i-1);
-      if (i != 1)
-        GC_end_stubborn_change(r);
+      struct treenode *x = libsrl_mktree(i - 1);
+      struct treenode *y = libsrl_mktree(i - 1);
+      r -> x = x;
+      r -> y = y;
+      if (i != 1) {
+        GC_END_STUBBORN_CHANGE(r);
+        GC_reachable_here(x);
+        GC_reachable_here(y);
+      }
     }
     return r;
   }
index cdded722613ea367fe0a381a3f73584299ca97fa..9a9780b7d8c271527aa28bf1d72ce7998fb6f07d 100644 (file)
@@ -326,7 +326,9 @@ sexpr cons (sexpr x, sexpr y)
     r -> sexpr_car = x;
     r -> sexpr_cdr = y;
     GC_END_STUBBORN_CHANGE(r);
-    return(r);
+    GC_reachable_here(x);
+    GC_reachable_here(y);
+    return r;
 }
 # endif
 
@@ -382,7 +384,9 @@ sexpr small_cons (sexpr x, sexpr y)
     r -> sexpr_car = x;
     r -> sexpr_cdr = y;
     GC_END_STUBBORN_CHANGE(r);
-    return(r);
+    GC_reachable_here(x);
+    GC_reachable_here(y);
+    return r;
 }
 
 #ifdef NO_CONS_ATOMIC_LEAF
@@ -409,7 +413,8 @@ sexpr small_cons_uncollectable (sexpr x, sexpr y)
     r -> sexpr_car = x;
     r -> sexpr_cdr = (sexpr)(~(GC_word)y);
     GC_END_STUBBORN_CHANGE(r);
-    return(r);
+    GC_reachable_here(x);
+    return r;
 }
 
 #ifdef GC_GCJ_SUPPORT
@@ -427,7 +432,9 @@ sexpr small_cons_uncollectable (sexpr x, sexpr y)
     result -> sexpr_car = x;
     result -> sexpr_cdr = y;
     GC_END_STUBBORN_CHANGE(r);
-    return(result);
+    GC_reachable_here(x);
+    GC_reachable_here(y);
+    return result;
   }
 #endif /* GC_GCJ_SUPPORT */
 
@@ -708,6 +715,7 @@ void *GC_CALLBACK reverse_test_inner(void *data)
     sexpr d;
     sexpr e;
     sexpr *f, *g, *h;
+    sexpr tmp;
 
     if (data == 0) {
       /* This stack frame is not guaranteed to be scanned. */
@@ -745,26 +753,42 @@ void *GC_CALLBACK reverse_test_inner(void *data)
     f = (sexpr *)GC_REALLOC((void *)f, 6 * sizeof(sexpr));
     CHECK_OUT_OF_MEMORY(f);
     AO_fetch_and_add1(&realloc_count);
-    f[5] = ints(1,17);
+    tmp = ints(1,17);
+    f[5] = tmp;
+    GC_END_STUBBORN_CHANGE(f + 5);
+    GC_reachable_here(tmp);
     AO_fetch_and_add1(&collectable_count);
     g = (sexpr *)GC_MALLOC(513 * sizeof(sexpr));
     test_generic_malloc_or_special(g);
     g = (sexpr *)GC_REALLOC((void *)g, 800 * sizeof(sexpr));
     CHECK_OUT_OF_MEMORY(g);
     AO_fetch_and_add1(&realloc_count);
-    g[799] = ints(1,18);
+    tmp = ints(1,18);
+    g[799] = tmp;
+    GC_END_STUBBORN_CHANGE(g + 799);
+    GC_reachable_here(tmp);
     AO_fetch_and_add1(&collectable_count);
     h = (sexpr *)GC_MALLOC(1025 * sizeof(sexpr));
     h = (sexpr *)GC_REALLOC((void *)h, 2000 * sizeof(sexpr));
     CHECK_OUT_OF_MEMORY(h);
     AO_fetch_and_add1(&realloc_count);
 #   ifdef GC_GCJ_SUPPORT
-      h[1999] = gcj_ints(1,200);
-      for (i = 0; i < 51; ++i)
-        h[1999] = gcj_reverse(h[1999]);
+      tmp = gcj_ints(1,200);
+      h[1999] = tmp;
+      GC_END_STUBBORN_CHANGE(h + 1999);
+      GC_reachable_here(tmp);
+      for (i = 0; i < 51; ++i) {
+        tmp = gcj_reverse(h[1999]);
+        h[1999] = tmp;
+        GC_END_STUBBORN_CHANGE(h + 1999);
+        GC_reachable_here(tmp);
+      }
       /* Leave it as the reversed list for now. */
 #   else
-      h[1999] = ints(1,200);
+      tmp = ints(1,200);
+      h[1999] = tmp;
+      GC_END_STUBBORN_CHANGE(h + 1999);
+      GC_reachable_here(tmp);
 #   endif
     /* Try to force some collections and reuse of small list elements */
     for (i = 0; i < 10; i++) {
@@ -813,7 +837,10 @@ void *GC_CALLBACK reverse_test_inner(void *data)
     check_ints(f[5], 1,17);
     check_ints(g[799], 1,18);
 #   ifdef GC_GCJ_SUPPORT
-      h[1999] = gcj_reverse(h[1999]);
+      tmp = gcj_reverse(h[1999]);
+      h[1999] = tmp;
+      GC_END_STUBBORN_CHANGE(h + 1999);
+      GC_reachable_here(tmp);
 #   endif
     check_ints(h[1999], 1,200);
 #   ifndef THREADS
@@ -878,6 +905,7 @@ int live_indicators_count = 0;
 tn * mktree(int n)
 {
     tn * result = GC_NEW(tn);
+    tn * left, * right;
 
     AO_fetch_and_add1(&collectable_count);
 #   if defined(MACOS)
@@ -891,20 +919,21 @@ tn * mktree(int n)
     if (n == 0) return(0);
     CHECK_OUT_OF_MEMORY(result);
     result -> level = n;
-    result -> lchild = mktree(n-1);
-    result -> rchild = mktree(n-1);
+    result -> lchild = left = mktree(n - 1);
+    result -> rchild = right = mktree(n - 1);
     if (AO_fetch_and_add1(&extra_count) % 17 == 0 && n >= 2) {
-        tn * tmp;
-        tn * left = result -> lchild;
-        tn * right = result -> rchild;
+        tn * tmp, * right_left;
 
         CHECK_OUT_OF_MEMORY(left);
         tmp = left -> rchild;
         CHECK_OUT_OF_MEMORY(right);
-        left -> rchild = right -> lchild;
+        right_left = right -> lchild;
+        left -> rchild = right_left;
         right -> lchild = tmp;
         GC_END_STUBBORN_CHANGE(left);
+        GC_reachable_here(right_left);
         GC_END_STUBBORN_CHANGE(right);
+        GC_reachable_here(tmp);
     }
     if (AO_fetch_and_add1(&extra_count) % 119 == 0) {
 #       ifndef GC_NO_FINALIZATION
@@ -996,6 +1025,8 @@ tn * mktree(int n)
       GC_reachable_here(result);
     }
     GC_END_STUBBORN_CHANGE(result);
+    GC_reachable_here(left);
+    GC_reachable_here(right);
     return(result);
 }
 
@@ -1035,6 +1066,7 @@ void * alloc8bytes(void)
 # else
     void ** my_free_list_ptr;
     void * my_free_list;
+    void * next;
 
     my_free_list_ptr = (void **)pthread_getspecific(fl_key);
     if (my_free_list_ptr == 0) {
@@ -1051,9 +1083,11 @@ void * alloc8bytes(void)
         my_free_list = GC_malloc_many(8);
         CHECK_OUT_OF_MEMORY(my_free_list);
     }
-    *my_free_list_ptr = GC_NEXT(my_free_list);
+    next = GC_NEXT(my_free_list);
+    *my_free_list_ptr = next;
     GC_NEXT(my_free_list) = 0;
     GC_END_STUBBORN_CHANGE(my_free_list_ptr);
+    GC_reachable_here(next);
     AO_fetch_and_add1(&collectable_count);
     return(my_free_list);
 # endif
@@ -1123,7 +1157,7 @@ void tree_test(void)
     }
     dropped_something = 1;
     FINALIZER_UNLOCK();
-    GC_noop1((word)root);       /* Root needs to remain live until      */
+    GC_reachable_here(root);    /* Root needs to remain live until      */
                                 /* dropped_something is set.            */
     root = mktree(TREE_HEIGHT);
     chktree(root, TREE_HEIGHT);
@@ -1199,6 +1233,7 @@ void typed_test(void)
         newP[0] = 17;
         newP[1] = (GC_word)old;
         GC_END_STUBBORN_CHANGE(newP);
+        GC_reachable_here(old);
         old = newP;
         AO_fetch_and_add1(&collectable_count);
         newP = (GC_word*)GC_malloc_explicitly_typed(33 * sizeof(GC_word), d3);
@@ -1206,6 +1241,7 @@ void typed_test(void)
         newP[0] = 17;
         newP[1] = (GC_word)old;
         GC_END_STUBBORN_CHANGE(newP);
+        GC_reachable_here(old);
         old = newP;
         AO_fetch_and_add1(&collectable_count);
         newP = (GC_word *)GC_calloc_explicitly_typed(4, 2 * sizeof(GC_word),
@@ -1214,6 +1250,7 @@ void typed_test(void)
         newP[0] = 17;
         newP[1] = (GC_word)old;
         GC_END_STUBBORN_CHANGE(newP);
+        GC_reachable_here(old);
         old = newP;
         AO_fetch_and_add1(&collectable_count);
         if (i & 0xff) {
@@ -1232,6 +1269,7 @@ void typed_test(void)
         newP[0] = 17;
         newP[1] = (GC_word)old;
         GC_END_STUBBORN_CHANGE(newP);
+        GC_reachable_here(old);
         old = newP;
     }
     for (i = 0; i < 20000; i++) {
index 493ec33d7f45ba52b356c83c7eb02e9b3c467566..840442f84d25f5fd3ac8ec8e526b0fc48090335a 100644 (file)
@@ -104,6 +104,18 @@ class B: public GC_NS_QUALIFY(gc), public A { public:
 
 int B::deleting = 0;
 
+#define C_INIT_LEFT_RIGHT(arg_l, arg_r) \
+    { \
+        C *l = new C(arg_l); \
+        C *r = new C(arg_r); \
+        left = l; \
+        right = r; \
+        if (GC_is_heap_ptr(this)) { \
+            GC_END_STUBBORN_CHANGE(this); \
+            GC_reachable_here(l); \
+            GC_reachable_here(r); \
+        } \
+    }
 
 class C: public GC_NS_QUALIFY(gc_cleanup), public A { public:
     /* A collectible class with cleanup and virtual multiple inheritance. */
@@ -112,12 +124,8 @@ class C: public GC_NS_QUALIFY(gc_cleanup), public A { public:
     // a copy constructor and an assignment operator to workaround a cppcheck
     // warning.
     C(const C& c) : A(c.i), level(c.level), left(0), right(0) {
-        if (level > 0) {
-            left = new C(*c.left);
-            right = new C(*c.right);
-            GC_end_stubborn_change(left);
-            GC_end_stubborn_change(right);
-        }
+        if (level > 0)
+            C_INIT_LEFT_RIGHT(*c.left, *c.right);
     }
 
     C& operator=(const C& c) {
@@ -128,12 +136,8 @@ class C: public GC_NS_QUALIFY(gc_cleanup), public A { public:
             level = c.level;
             left = 0;
             right = 0;
-            if (level > 0) {
-                left = new C(*c.left);
-                right = new C(*c.right);
-                GC_end_stubborn_change(left);
-                GC_end_stubborn_change(right);
-            }
+            if (level > 0)
+                C_INIT_LEFT_RIGHT(*c.left, *c.right);
         }
         return *this;
     }
@@ -141,10 +145,7 @@ class C: public GC_NS_QUALIFY(gc_cleanup), public A { public:
     GC_ATTR_EXPLICIT C( int levelArg ): A( levelArg ), level( levelArg ) {
         nAllocated++;
         if (level > 0) {
-            left = new C( level - 1 );
-            right = new C( level - 1 );
-            GC_end_stubborn_change(left);
-            GC_end_stubborn_change(right);
+            C_INIT_LEFT_RIGHT(level - 1, level - 1);
         } else {
             left = right = 0;}}
     ~C() {
@@ -319,7 +320,8 @@ void* Undisguise( GC_word i ) {
         exit(3);
       }
       *xptr = x;
-      GC_end_stubborn_change(xptr);
+      GC_END_STUBBORN_CHANGE(xptr);
+      GC_reachable_here(x);
       x = 0;
 #   endif
     if (argc != 2
@@ -345,7 +347,6 @@ void* Undisguise( GC_word i ) {
             Later we'll check to make sure they've gone away. */
         for (i = 0; i < 1000; i++) {
             C* c = new C( 2 );
-            GC_end_stubborn_change(c);
             C c1( 2 );           /* stack allocation should work too */
             D* d;
             F* f;
index 1bcf07bb194b332362b32046cf5a3cc6c6a85c83..726519d0c56227f51db0307c00d0f09e8d8fbfc7 100644 (file)
@@ -15,6 +15,7 @@ struct treenode {
 
 struct treenode * mktree(int i) {
   struct treenode * r = GC_NEW(struct treenode);
+  struct treenode *x, *y;
   if (0 == i)
     return 0;
   if (1 == i)
@@ -23,10 +24,15 @@ struct treenode * mktree(int i) {
     fprintf(stderr, "Out of memory\n");
     exit(1);
   }
-  r -> x = mktree(i-1);
-  r -> y = mktree(i-1);
-  if (i != 1)
-    GC_end_stubborn_change(r);
+  x = mktree(i - 1);
+  y = mktree(i - 1);
+  r -> x = x;
+  r -> y = y;
+  if (i != 1) {
+    GC_END_STUBBORN_CHANGE(r);
+    GC_reachable_here(x);
+    GC_reachable_here(y);
+  }
   return r;
 }