< prev index next >

src/share/vm/gc_implementation/g1/g1Allocator.hpp

Print this page
rev 8152 : secret commit PLAB waste


 166     if (_retired) {
 167       return;
 168     }
 169     PLAB::retire();
 170     _retired = true;
 171   }
 172 };
 173 
 174 class G1ParGCAllocator : public CHeapObj<mtGC> {
 175   friend class G1ParScanThreadState;
 176 protected:
 177   G1CollectedHeap* _g1h;
 178 
 179   // The survivor alignment in effect in bytes.
 180   // == 0 : don't align survivors
 181   // != 0 : align survivors to that alignment
 182   // These values were chosen to favor the non-alignment case since some
 183   // architectures have a special compare against zero instructions.
 184   const uint _survivor_alignment_bytes;
 185 
 186   size_t _alloc_buffer_waste;
 187   size_t _undo_waste;
 188 
 189   void add_to_alloc_buffer_waste(size_t waste) { _alloc_buffer_waste += waste; }
 190   void add_to_undo_waste(size_t waste)         { _undo_waste += waste; }
 191 
 192   virtual void retire_alloc_buffers() = 0;
 193   virtual G1PLAB* alloc_buffer(InCSetState dest, AllocationContext_t context) = 0;
 194 
 195   // Calculate the survivor space object alignment in bytes. Returns that or 0 if
 196   // there are no restrictions on survivor alignment.
 197   static uint calc_survivor_alignment_bytes() {
 198     assert(SurvivorAlignmentInBytes >= ObjectAlignmentInBytes, "sanity");
 199     if (SurvivorAlignmentInBytes == ObjectAlignmentInBytes) {
 200       // No need to align objects in the survivors differently, return 0
 201       // which means "survivor alignment is not used".
 202       return 0;
 203     } else {
 204       assert(SurvivorAlignmentInBytes > 0, "sanity");
 205       return SurvivorAlignmentInBytes;
 206     }
 207   }
 208 
 209 public:
 210   G1ParGCAllocator(G1CollectedHeap* g1h) :
 211     _g1h(g1h), _survivor_alignment_bytes(calc_survivor_alignment_bytes()),
 212     _alloc_buffer_waste(0), _undo_waste(0) {
 213   }
 214 
 215   static G1ParGCAllocator* create_allocator(G1CollectedHeap* g1h);
 216 
 217   size_t alloc_buffer_waste() { return _alloc_buffer_waste; }
 218   size_t undo_waste() {return _undo_waste; }
 219 
 220   // Allocate word_sz words in dest, either directly into the regions or by
 221   // allocating a new PLAB. Returns the address of the allocated memory, NULL if
 222   // not successful.
 223   HeapWord* allocate_direct_or_new_plab(InCSetState dest,
 224                                         size_t word_sz,
 225                                         AllocationContext_t context);
 226 
 227   // Allocate word_sz words in the PLAB of dest.  Returns the address of the
 228   // allocated memory, NULL if not successful.
 229   HeapWord* plab_allocate(InCSetState dest,
 230                           size_t word_sz,
 231                           AllocationContext_t context) {
 232     G1PLAB* buffer = alloc_buffer(dest, context);
 233     if (_survivor_alignment_bytes == 0) {
 234       return buffer->allocate(word_sz);
 235     } else {
 236       return buffer->allocate_aligned(word_sz, _survivor_alignment_bytes);
 237     }
 238   }
 239 
 240   HeapWord* allocate(InCSetState dest, size_t word_sz,
 241                      AllocationContext_t context) {
 242     HeapWord* const obj = plab_allocate(dest, word_sz, context);
 243     if (obj != NULL) {
 244       return obj;
 245     }
 246     return allocate_direct_or_new_plab(dest, word_sz, context);
 247   }
 248 
 249   void undo_allocation(InCSetState dest, HeapWord* obj, size_t word_sz, AllocationContext_t context) {
 250     if (alloc_buffer(dest, context)->contains(obj)) {
 251       assert(alloc_buffer(dest, context)->contains(obj + word_sz - 1),
 252              "should contain whole object");
 253       alloc_buffer(dest, context)->undo_allocation(obj, word_sz);
 254     } else {
 255       CollectedHeap::fill_with_object(obj, word_sz);
 256       add_to_undo_waste(word_sz);
 257     }
 258   }
 259 };
 260 
 261 class G1DefaultParGCAllocator : public G1ParGCAllocator {
 262   G1PLAB  _surviving_alloc_buffer;
 263   G1PLAB  _tenured_alloc_buffer;
 264   G1PLAB* _alloc_buffers[InCSetState::Num];
 265 
 266 public:
 267   G1DefaultParGCAllocator(G1CollectedHeap* g1h);
 268 
 269   virtual G1PLAB* alloc_buffer(InCSetState dest, AllocationContext_t context) {
 270     assert(dest.is_valid(),
 271            err_msg("Allocation buffer index out-of-bounds: " CSETSTATE_FORMAT, dest.value()));
 272     assert(_alloc_buffers[dest.value()] != NULL,
 273            err_msg("Allocation buffer is NULL: " CSETSTATE_FORMAT, dest.value()));
 274     return _alloc_buffers[dest.value()];
 275   }
 276 
 277   virtual void retire_alloc_buffers() ;


 278 };
 279 
 280 #endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1ALLOCATOR_HPP


 166     if (_retired) {
 167       return;
 168     }
 169     PLAB::retire();
 170     _retired = true;
 171   }
 172 };
 173 
 174 class G1ParGCAllocator : public CHeapObj<mtGC> {
 175   friend class G1ParScanThreadState;
 176 protected:
 177   G1CollectedHeap* _g1h;
 178 
 179   // The survivor alignment in effect in bytes.
 180   // == 0 : don't align survivors
 181   // != 0 : align survivors to that alignment
 182   // These values were chosen to favor the non-alignment case since some
 183   // architectures have a special compare against zero instructions.
 184   const uint _survivor_alignment_bytes;
 185 






 186   virtual void retire_alloc_buffers() = 0;
 187   virtual G1PLAB* alloc_buffer(InCSetState dest, AllocationContext_t context) = 0;
 188 
 189   // Calculate the survivor space object alignment in bytes. Returns that or 0 if
 190   // there are no restrictions on survivor alignment.
 191   static uint calc_survivor_alignment_bytes() {
 192     assert(SurvivorAlignmentInBytes >= ObjectAlignmentInBytes, "sanity");
 193     if (SurvivorAlignmentInBytes == ObjectAlignmentInBytes) {
 194       // No need to align objects in the survivors differently, return 0
 195       // which means "survivor alignment is not used".
 196       return 0;
 197     } else {
 198       assert(SurvivorAlignmentInBytes > 0, "sanity");
 199       return SurvivorAlignmentInBytes;
 200     }
 201   }
 202 
 203 public:
 204   G1ParGCAllocator(G1CollectedHeap* g1h) :
 205     _g1h(g1h), _survivor_alignment_bytes(calc_survivor_alignment_bytes()) {

 206   }
 207 
 208   static G1ParGCAllocator* create_allocator(G1CollectedHeap* g1h);
 209 
 210   virtual void waste(size_t& wasted, size_t& undo_wasted) = 0;

 211   
 212   // Allocate word_sz words in dest, either directly into the regions or by
 213   // allocating a new PLAB. Returns the address of the allocated memory, NULL if
 214   // not successful.
 215   HeapWord* allocate_direct_or_new_plab(InCSetState dest,
 216                                         size_t word_sz,
 217                                         AllocationContext_t context);
 218 
 219   // Allocate word_sz words in the PLAB of dest.  Returns the address of the
 220   // allocated memory, NULL if not successful.
 221   HeapWord* plab_allocate(InCSetState dest,
 222                           size_t word_sz,
 223                           AllocationContext_t context) {
 224     G1PLAB* buffer = alloc_buffer(dest, context);
 225     if (_survivor_alignment_bytes == 0) {
 226       return buffer->allocate(word_sz);
 227     } else {
 228       return buffer->allocate_aligned(word_sz, _survivor_alignment_bytes);
 229     }
 230   }
 231 
 232   HeapWord* allocate(InCSetState dest, size_t word_sz,
 233                      AllocationContext_t context) {
 234     HeapWord* const obj = plab_allocate(dest, word_sz, context);
 235     if (obj != NULL) {
 236       return obj;
 237     }
 238     return allocate_direct_or_new_plab(dest, word_sz, context);
 239   }
 240 
 241   void undo_allocation(InCSetState dest, HeapWord* obj, size_t word_sz, AllocationContext_t context) {



 242     alloc_buffer(dest, context)->undo_allocation(obj, word_sz);




 243   }
 244 };
 245 
 246 class G1DefaultParGCAllocator : public G1ParGCAllocator {
 247   G1PLAB  _surviving_alloc_buffer;
 248   G1PLAB  _tenured_alloc_buffer;
 249   G1PLAB* _alloc_buffers[InCSetState::Num];
 250 
 251 public:
 252   G1DefaultParGCAllocator(G1CollectedHeap* g1h);
 253 
 254   virtual G1PLAB* alloc_buffer(InCSetState dest, AllocationContext_t context) {
 255     assert(dest.is_valid(),
 256            err_msg("Allocation buffer index out-of-bounds: " CSETSTATE_FORMAT, dest.value()));
 257     assert(_alloc_buffers[dest.value()] != NULL,
 258            err_msg("Allocation buffer is NULL: " CSETSTATE_FORMAT, dest.value()));
 259     return _alloc_buffers[dest.value()];
 260   }
 261 
 262   virtual void retire_alloc_buffers();
 263 
 264   virtual void waste(size_t& wasted, size_t& undo_wasted);
 265 };
 266 
 267 #endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1ALLOCATOR_HPP
< prev index next >