< prev index next >

src/share/vm/gc_implementation/concurrentMarkSweep/compactibleFreeListSpace.cpp

Print this page
rev 9232 : 8248851: CMS: Missing memory fences between free chunk check and klass read
Reviewed-by: aph
Contributed-by: wangshuai94@huawei.com

@@ -992,10 +992,14 @@
       if (FreeChunk::indicatesFreeChunk(p)) {
         assert(res != 0, "Block size should not be 0");
         return res;
       }
     } else {
+      // Acquire to make sure that the klass read happens after the free
+      // chunk check.
+      OrderAccess::acquire();
+
       // must read from what 'p' points to in each loop.
       Klass* k = ((volatile oopDesc*)p)->klass_or_null();
       if (k != NULL) {
         assert(k->is_klass(), "Should really be klass oop.");
         oop o = (oop)p;

@@ -1047,10 +1051,14 @@
         assert(res != 0, "Block size should not be 0");
         assert(loops == 0, "Should be 0");
         return res;
       }
     } else {
+      // Acquire to make sure that the klass read happens after the free
+      // chunk check.
+      OrderAccess::acquire();
+
       // must read from what 'p' points to in each loop.
       Klass* k = ((volatile oopDesc*)p)->klass_or_null();
       // We trust the size of any object that has a non-NULL
       // klass and (for those in the perm gen) is parsable
       // -- irrespective of its conc_safe-ty.

@@ -1109,10 +1117,15 @@
   // and those objects (if garbage) may have been modified to hold
   // live range information.
   // assert(CollectedHeap::use_parallel_gc_threads() || _bt.block_start(p) == p,
   //        "Should be a block boundary");
   if (FreeChunk::indicatesFreeChunk(p)) return false;
+
+  // Acquire to make sure that the klass read happens after the free
+  // chunk check.
+  OrderAccess::acquire();
+
   Klass* k = oop(p)->klass_or_null();
   if (k != NULL) {
     // Ignore mark word because it may have been used to
     // chain together promoted objects (the last one
     // would have a null value).
< prev index next >