1 /*
   2  * Copyright (c) 2015, 2018, Red Hat, Inc. All rights reserved.
   3  *
   4  * This code is free software; you can redistribute it and/or modify it
   5  * under the terms of the GNU General Public License version 2 only, as
   6  * published by the Free Software Foundation.
   7  *
   8  * This code is distributed in the hope that it will be useful, but WITHOUT
   9  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  10  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  11  * version 2 for more details (a copy is included in the LICENSE file that
  12  * accompanied this code).
  13  *
  14  * You should have received a copy of the GNU General Public License version
  15  * 2 along with this work; if not, write to the Free Software Foundation,
  16  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  17  *
  18  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  19  * or visit www.oracle.com if you need additional information or have any
  20  * questions.
  21  *
  22  */
  23 
  24 #ifndef SHARE_VM_GC_SHENANDOAH_SHENANDOAHOOPCLOSURES_HPP
  25 #define SHARE_VM_GC_SHENANDOAH_SHENANDOAHOOPCLOSURES_HPP
  26 
  27 #include "memory/iterator.hpp"
  28 #include "gc_implementation/shenandoah/shenandoahTaskqueue.hpp"
  29 
  30 class ShenandoahHeap;
  31 class ShenandoahStrDedupQueue;
  32 class ShenandoahMarkingContext;
  33 class OopClosure;
  34 
  35 enum UpdateRefsMode {
  36   NONE,       // No reference updating
  37   RESOLVE,    // Only a read-barrier (no reference updating)
  38   SIMPLE,     // Reference updating using simple store
  39   CONCURRENT  // Reference updating using CAS
  40 };
  41 
  42 enum StringDedupMode {
  43   NO_DEDUP,      // Do not do anything for String deduplication
  44   ENQUEUE_DEDUP  // Enqueue candidate Strings for deduplication
  45 };
  46 
  47 class ShenandoahMarkRefsSuperClosure : public MetadataAwareOopClosure {
  48 private:
  49   ShenandoahObjToScanQueue* _queue;
  50   ShenandoahStrDedupQueue*  _dedup_queue;
  51   ShenandoahHeap* _heap;
  52   ShenandoahMarkingContext* const _mark_context;
  53 
  54 public:
  55   ShenandoahMarkRefsSuperClosure(ShenandoahObjToScanQueue* q, ReferenceProcessor* rp);
  56   ShenandoahMarkRefsSuperClosure(ShenandoahObjToScanQueue* q, ShenandoahStrDedupQueue* dq, ReferenceProcessor* rp);
  57 
  58   template <class T, UpdateRefsMode UPDATE_MODE, StringDedupMode STRING_DEDUP>
  59   void work(T *p);
  60 };
  61 
  62 class ShenandoahMarkUpdateRefsClosure : public ShenandoahMarkRefsSuperClosure {
  63 public:
  64   ShenandoahMarkUpdateRefsClosure(ShenandoahObjToScanQueue* q, ReferenceProcessor* rp) :
  65           ShenandoahMarkRefsSuperClosure(q, rp) {};
  66 
  67   template <class T>
  68   inline void do_oop_nv(T* p)       { work<T, CONCURRENT, NO_DEDUP>(p); }
  69   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
  70   virtual void do_oop(oop* p)       { do_oop_nv(p); }
  71   inline bool do_metadata_nv()      { return false; }
  72   virtual bool do_metadata()        { return false; }
  73 };
  74 
  75 class ShenandoahMarkUpdateRefsDedupClosure : public ShenandoahMarkRefsSuperClosure {
  76 public:
  77   ShenandoahMarkUpdateRefsDedupClosure(ShenandoahObjToScanQueue* q, ShenandoahStrDedupQueue* dq, ReferenceProcessor* rp) :
  78           ShenandoahMarkRefsSuperClosure(q, dq, rp) {};
  79 
  80   template <class T>
  81   inline void do_oop_nv(T* p)       { work<T, CONCURRENT, ENQUEUE_DEDUP>(p); }
  82   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
  83   virtual void do_oop(oop* p)       { do_oop_nv(p); }
  84   inline bool do_metadata_nv()      { return false; }
  85   virtual bool do_metadata()        { return false; }
  86 };
  87 
  88 class ShenandoahMarkUpdateRefsMetadataClosure : public ShenandoahMarkRefsSuperClosure {
  89 public:
  90   ShenandoahMarkUpdateRefsMetadataClosure(ShenandoahObjToScanQueue* q, ReferenceProcessor* rp) :
  91     ShenandoahMarkRefsSuperClosure(q, rp) {};
  92 
  93   template <class T>
  94   inline void do_oop_nv(T* p)       { work<T, CONCURRENT, NO_DEDUP>(p); }
  95   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
  96   virtual void do_oop(oop* p)       { do_oop_nv(p); }
  97   inline bool do_metadata_nv()      { return true; }
  98   virtual bool do_metadata()        { return true; }
  99 };
 100 
 101 class ShenandoahMarkUpdateRefsMetadataDedupClosure : public ShenandoahMarkRefsSuperClosure {
 102 public:
 103   ShenandoahMarkUpdateRefsMetadataDedupClosure(ShenandoahObjToScanQueue* q, ShenandoahStrDedupQueue* dq, ReferenceProcessor* rp) :
 104   ShenandoahMarkRefsSuperClosure(q, dq, rp) {};
 105 
 106   template <class T>
 107   inline void do_oop_nv(T* p)       { work<T, CONCURRENT, ENQUEUE_DEDUP>(p); }
 108   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 109   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 110   inline bool do_metadata_nv()      { return true; }
 111   virtual bool do_metadata()        { return true; }
 112 };
 113 
 114 class ShenandoahMarkRefsClosure : public ShenandoahMarkRefsSuperClosure {
 115 public:
 116   ShenandoahMarkRefsClosure(ShenandoahObjToScanQueue* q, ReferenceProcessor* rp) :
 117     ShenandoahMarkRefsSuperClosure(q, rp) {};
 118 
 119   template <class T>
 120   inline void do_oop_nv(T* p)       { work<T, NONE, NO_DEDUP>(p); }
 121   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 122   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 123   inline bool do_metadata_nv()      { return false; }
 124   virtual bool do_metadata()        { return false; }
 125 };
 126 
 127 class ShenandoahMarkRefsDedupClosure : public ShenandoahMarkRefsSuperClosure {
 128 public:
 129   ShenandoahMarkRefsDedupClosure(ShenandoahObjToScanQueue* q, ShenandoahStrDedupQueue* dq, ReferenceProcessor* rp) :
 130     ShenandoahMarkRefsSuperClosure(q, dq, rp) {};
 131 
 132   template <class T>
 133   inline void do_oop_nv(T* p)       { work<T, NONE, ENQUEUE_DEDUP>(p); }
 134   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 135   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 136   inline bool do_metadata_nv()      { return false; }
 137   virtual bool do_metadata()        { return false; }
 138 };
 139 
 140 class ShenandoahMarkResolveRefsClosure : public ShenandoahMarkRefsSuperClosure {
 141 public:
 142   ShenandoahMarkResolveRefsClosure(ShenandoahObjToScanQueue* q, ReferenceProcessor* rp) :
 143     ShenandoahMarkRefsSuperClosure(q, rp) {};
 144 
 145   template <class T>
 146   inline void do_oop_nv(T* p)       { work<T, RESOLVE, NO_DEDUP>(p); }
 147   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 148   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 149   inline bool do_metadata_nv()      { return false; }
 150   virtual bool do_metadata()        { return false; }
 151 };
 152 
 153 class ShenandoahMarkResolveRefsDedupClosure : public ShenandoahMarkRefsSuperClosure {
 154 public:
 155   ShenandoahMarkResolveRefsDedupClosure(ShenandoahObjToScanQueue* q, ShenandoahStrDedupQueue* dq, ReferenceProcessor* rp) :
 156     ShenandoahMarkRefsSuperClosure(q, dq, rp) {};
 157 
 158   template <class T>
 159   inline void do_oop_nv(T* p)       { work<T, RESOLVE, ENQUEUE_DEDUP>(p); }
 160   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 161   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 162   inline bool do_metadata_nv()      { return false; }
 163   virtual bool do_metadata()        { return false; }
 164 };
 165 
 166 class ShenandoahMarkRefsMetadataClosure : public ShenandoahMarkRefsSuperClosure {
 167 public:
 168   ShenandoahMarkRefsMetadataClosure(ShenandoahObjToScanQueue* q, ReferenceProcessor* rp) :
 169     ShenandoahMarkRefsSuperClosure(q, rp) {};
 170 
 171   template <class T>
 172   inline void do_oop_nv(T* p)       { work<T, NONE, NO_DEDUP>(p); }
 173   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 174   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 175   inline bool do_metadata_nv()      { return true; }
 176   virtual bool do_metadata()        { return true; }
 177 };
 178 
 179 class ShenandoahMarkRefsMetadataDedupClosure : public ShenandoahMarkRefsSuperClosure {
 180 public:
 181   ShenandoahMarkRefsMetadataDedupClosure(ShenandoahObjToScanQueue* q, ShenandoahStrDedupQueue* dq, ReferenceProcessor* rp) :
 182     ShenandoahMarkRefsSuperClosure(q, dq, rp) {};
 183 
 184   template <class T>
 185   inline void do_oop_nv(T* p)       { work<T, NONE, ENQUEUE_DEDUP>(p); }
 186   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 187   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 188   inline bool do_metadata_nv()      { return true; }
 189   virtual bool do_metadata()        { return true; }
 190 };
 191 
 192 class ShenandoahUpdateHeapRefsClosure : public ExtendedOopClosure {
 193 private:
 194   ShenandoahHeap* _heap;
 195 public:
 196   ShenandoahUpdateHeapRefsClosure();
 197 
 198   template <class T>
 199   void do_oop_nv(T* p);
 200 
 201   virtual void do_oop(narrowOop* p) { do_oop_nv(p); }
 202   virtual void do_oop(oop* p)       { do_oop_nv(p); }
 203 };
 204 
 205 #endif // SHARE_VM_GC_SHENANDOAH_SHENANDOAHOOPCLOSURES_HPP