< prev index next >

src/share/vm/memory/metaspace.cpp

Print this page
rev 8039 : [mq]: container_count


 329   VirtualSpaceNode* next() { return _next; }
 330   void set_next(VirtualSpaceNode* v) { _next = v; }
 331 
 332   void set_reserved(MemRegion const v) { _reserved = v; }
 333   void set_top(MetaWord* v) { _top = v; }
 334 
 335   // Accessors
 336   MemRegion* reserved() { return &_reserved; }
 337   VirtualSpace* virtual_space() const { return (VirtualSpace*) &_virtual_space; }
 338 
 339   // Returns true if "word_size" is available in the VirtualSpace
 340   bool is_available(size_t word_size) { return word_size <= pointer_delta(end(), _top, sizeof(MetaWord)); }
 341 
 342   MetaWord* top() const { return _top; }
 343   void inc_top(size_t word_size) { _top += word_size; }
 344 
 345   uintx container_count() { return _container_count; }
 346   void inc_container_count();
 347   void dec_container_count();
 348 #ifdef ASSERT
 349   uint container_count_slow();
 350   void verify_container_count();
 351 #endif
 352 
 353   // used and capacity in this single entry in the list
 354   size_t used_words_in_vs() const;
 355   size_t capacity_words_in_vs() const;
 356 
 357   bool initialize();
 358 
 359   // get space from the virtual space
 360   Metachunk* take_from_committed(size_t chunk_word_size);
 361 
 362   // Allocate a chunk from the virtual space and return it.
 363   Metachunk* get_chunk_vs(size_t chunk_word_size);
 364 
 365   // Expands/shrinks the committed space in a virtual space.  Delegates
 366   // to Virtualspace
 367   bool expand_by(size_t min_words, size_t preferred_words);
 368 
 369   // In preparation for deleting this node, remove all the chunks


 446 
 447     MemTracker::record_virtual_memory_type((address)_rs.base(), mtClass);
 448   }
 449 }
 450 
 451 void VirtualSpaceNode::purge(ChunkManager* chunk_manager) {
 452   Metachunk* chunk = first_chunk();
 453   Metachunk* invalid_chunk = (Metachunk*) top();
 454   while (chunk < invalid_chunk ) {
 455     assert(chunk->is_tagged_free(), "Should be tagged free");
 456     MetaWord* next = ((MetaWord*)chunk) + chunk->word_size();
 457     chunk_manager->remove_chunk(chunk);
 458     assert(chunk->next() == NULL &&
 459            chunk->prev() == NULL,
 460            "Was not removed from its list");
 461     chunk = (Metachunk*) next;
 462   }
 463 }
 464 
 465 #ifdef ASSERT
 466 uint VirtualSpaceNode::container_count_slow() {
 467   uint count = 0;
 468   Metachunk* chunk = first_chunk();
 469   Metachunk* invalid_chunk = (Metachunk*) top();
 470   while (chunk < invalid_chunk ) {
 471     MetaWord* next = ((MetaWord*)chunk) + chunk->word_size();
 472     // Don't count the chunks on the free lists.  Those are
 473     // still part of the VirtualSpaceNode but not currently
 474     // counted.
 475     if (!chunk->is_tagged_free()) {
 476       count++;
 477     }
 478     chunk = (Metachunk*) next;
 479   }
 480   return count;
 481 }
 482 #endif
 483 
 484 // List of VirtualSpaces for metadata allocation.
 485 class VirtualSpaceList : public CHeapObj<mtClass> {
 486   friend class VirtualSpaceNode;
 487 


 781     assert(raw_word_size * BytesPerWord == raw_bytes_size, "Size problem");
 782 
 783     return raw_word_size;
 784   }
 785 };
 786 
 787 uint const SpaceManager::_small_chunk_limit = 4;
 788 
 789 const char* SpaceManager::_expand_lock_name =
 790   "SpaceManager chunk allocation lock";
 791 const int SpaceManager::_expand_lock_rank = Monitor::leaf - 1;
 792 Mutex* const SpaceManager::_expand_lock =
 793   new Mutex(SpaceManager::_expand_lock_rank,
 794             SpaceManager::_expand_lock_name,
 795             Mutex::_allow_vm_block_flag,
 796             Monitor::_safepoint_check_never);
 797 
 798 void VirtualSpaceNode::inc_container_count() {
 799   assert_lock_strong(SpaceManager::expand_lock());
 800   _container_count++;
 801   assert(_container_count == container_count_slow(),
 802          err_msg("Inconsistency in container_count _container_count " SIZE_FORMAT
 803                  " container_count_slow() " SIZE_FORMAT,
 804                  _container_count, container_count_slow()));
 805 }
 806 
 807 void VirtualSpaceNode::dec_container_count() {
 808   assert_lock_strong(SpaceManager::expand_lock());
 809   _container_count--;
 810 }
 811 
 812 #ifdef ASSERT
 813 void VirtualSpaceNode::verify_container_count() {
 814   assert(_container_count == container_count_slow(),
 815     err_msg("Inconsistency in container_count _container_count " SIZE_FORMAT
 816             " container_count_slow() " SIZE_FORMAT, _container_count, container_count_slow()));
 817 }
 818 #endif
 819 
 820 // BlockFreelist methods
 821 
 822 BlockFreelist::BlockFreelist() : _dictionary(NULL) {}
 823 
 824 BlockFreelist::~BlockFreelist() {
 825   if (_dictionary != NULL) {
 826     if (Verbose && TraceMetadataChunkAllocation) {
 827       _dictionary->print_free_lists(gclog_or_tty);
 828     }
 829     delete _dictionary;
 830   }
 831 }
 832 
 833 void BlockFreelist::return_block(MetaWord* p, size_t word_size) {
 834   Metablock* free_chunk = ::new (p) Metablock(word_size);
 835   if (dictionary() == NULL) {
 836    _dictionary = new BlockTreeDictionary();




 329   VirtualSpaceNode* next() { return _next; }
 330   void set_next(VirtualSpaceNode* v) { _next = v; }
 331 
 332   void set_reserved(MemRegion const v) { _reserved = v; }
 333   void set_top(MetaWord* v) { _top = v; }
 334 
 335   // Accessors
 336   MemRegion* reserved() { return &_reserved; }
 337   VirtualSpace* virtual_space() const { return (VirtualSpace*) &_virtual_space; }
 338 
 339   // Returns true if "word_size" is available in the VirtualSpace
 340   bool is_available(size_t word_size) { return word_size <= pointer_delta(end(), _top, sizeof(MetaWord)); }
 341 
 342   MetaWord* top() const { return _top; }
 343   void inc_top(size_t word_size) { _top += word_size; }
 344 
 345   uintx container_count() { return _container_count; }
 346   void inc_container_count();
 347   void dec_container_count();
 348 #ifdef ASSERT
 349   uintx container_count_slow();
 350   void verify_container_count();
 351 #endif
 352 
 353   // used and capacity in this single entry in the list
 354   size_t used_words_in_vs() const;
 355   size_t capacity_words_in_vs() const;
 356 
 357   bool initialize();
 358 
 359   // get space from the virtual space
 360   Metachunk* take_from_committed(size_t chunk_word_size);
 361 
 362   // Allocate a chunk from the virtual space and return it.
 363   Metachunk* get_chunk_vs(size_t chunk_word_size);
 364 
 365   // Expands/shrinks the committed space in a virtual space.  Delegates
 366   // to Virtualspace
 367   bool expand_by(size_t min_words, size_t preferred_words);
 368 
 369   // In preparation for deleting this node, remove all the chunks


 446 
 447     MemTracker::record_virtual_memory_type((address)_rs.base(), mtClass);
 448   }
 449 }
 450 
 451 void VirtualSpaceNode::purge(ChunkManager* chunk_manager) {
 452   Metachunk* chunk = first_chunk();
 453   Metachunk* invalid_chunk = (Metachunk*) top();
 454   while (chunk < invalid_chunk ) {
 455     assert(chunk->is_tagged_free(), "Should be tagged free");
 456     MetaWord* next = ((MetaWord*)chunk) + chunk->word_size();
 457     chunk_manager->remove_chunk(chunk);
 458     assert(chunk->next() == NULL &&
 459            chunk->prev() == NULL,
 460            "Was not removed from its list");
 461     chunk = (Metachunk*) next;
 462   }
 463 }
 464 
 465 #ifdef ASSERT
 466 uintx VirtualSpaceNode::container_count_slow() {
 467   uintx count = 0;
 468   Metachunk* chunk = first_chunk();
 469   Metachunk* invalid_chunk = (Metachunk*) top();
 470   while (chunk < invalid_chunk ) {
 471     MetaWord* next = ((MetaWord*)chunk) + chunk->word_size();
 472     // Don't count the chunks on the free lists.  Those are
 473     // still part of the VirtualSpaceNode but not currently
 474     // counted.
 475     if (!chunk->is_tagged_free()) {
 476       count++;
 477     }
 478     chunk = (Metachunk*) next;
 479   }
 480   return count;
 481 }
 482 #endif
 483 
 484 // List of VirtualSpaces for metadata allocation.
 485 class VirtualSpaceList : public CHeapObj<mtClass> {
 486   friend class VirtualSpaceNode;
 487 


 781     assert(raw_word_size * BytesPerWord == raw_bytes_size, "Size problem");
 782 
 783     return raw_word_size;
 784   }
 785 };
 786 
 787 uint const SpaceManager::_small_chunk_limit = 4;
 788 
 789 const char* SpaceManager::_expand_lock_name =
 790   "SpaceManager chunk allocation lock";
 791 const int SpaceManager::_expand_lock_rank = Monitor::leaf - 1;
 792 Mutex* const SpaceManager::_expand_lock =
 793   new Mutex(SpaceManager::_expand_lock_rank,
 794             SpaceManager::_expand_lock_name,
 795             Mutex::_allow_vm_block_flag,
 796             Monitor::_safepoint_check_never);
 797 
 798 void VirtualSpaceNode::inc_container_count() {
 799   assert_lock_strong(SpaceManager::expand_lock());
 800   _container_count++;
 801   DEBUG_ONLY(verify_container_count();)



 802 }
 803 
 804 void VirtualSpaceNode::dec_container_count() {
 805   assert_lock_strong(SpaceManager::expand_lock());
 806   _container_count--;
 807 }
 808 
 809 #ifdef ASSERT
 810 void VirtualSpaceNode::verify_container_count() {
 811   assert(_container_count == container_count_slow(),
 812     err_msg("Inconsistency in container_count _container_count " UINTX_FORMAT
 813             " container_count_slow() " UINTX_FORMAT, _container_count, container_count_slow()));
 814 }
 815 #endif
 816 
 817 // BlockFreelist methods
 818 
 819 BlockFreelist::BlockFreelist() : _dictionary(NULL) {}
 820 
 821 BlockFreelist::~BlockFreelist() {
 822   if (_dictionary != NULL) {
 823     if (Verbose && TraceMetadataChunkAllocation) {
 824       _dictionary->print_free_lists(gclog_or_tty);
 825     }
 826     delete _dictionary;
 827   }
 828 }
 829 
 830 void BlockFreelist::return_block(MetaWord* p, size_t word_size) {
 831   Metablock* free_chunk = ::new (p) Metablock(word_size);
 832   if (dictionary() == NULL) {
 833    _dictionary = new BlockTreeDictionary();


< prev index next >