changeset 2092:51bd2d261853

7008325: CodeCache exhausted on sparc starting from hs20b04 Summary: remove clear_scratch_buffer_blob and let init_scratch_buffer_blob free and allocate a new blob if required. Reviewed-by: twisti
author kvn
date Wed, 29 Dec 2010 10:41:43 -0800
parents 2ddb2fab82cb
children 68c5a4e8881d
files src/share/vm/code/codeCache.cpp src/share/vm/code/codeCache.hpp src/share/vm/memory/heap.cpp src/share/vm/memory/heap.hpp src/share/vm/opto/compile.cpp src/share/vm/opto/output.cpp
diffstat 6 files changed, 39 insertions(+), 26 deletions(-) [+]
line wrap: on
line diff
--- a/src/share/vm/code/codeCache.cpp	Tue Dec 28 17:34:02 2010 -0800
+++ b/src/share/vm/code/codeCache.cpp	Wed Dec 29 10:41:43 2010 -0800
@@ -939,7 +939,9 @@
                _heap->high(),
                _heap->high_boundary());
   st->print_cr(" total_blobs=" UINT32_FORMAT " nmethods=" UINT32_FORMAT
-               " adapters=" UINT32_FORMAT " free_code_cache=" SIZE_FORMAT,
+               " adapters=" UINT32_FORMAT " free_code_cache=" SIZE_FORMAT
+               " largest_free_block=" SIZE_FORMAT,
                CodeCache::nof_blobs(), CodeCache::nof_nmethods(),
-               CodeCache::nof_adapters(), CodeCache::unallocated_capacity());
+               CodeCache::nof_adapters(), CodeCache::unallocated_capacity(),
+               CodeCache::largest_free_block());
 }
--- a/src/share/vm/code/codeCache.hpp	Tue Dec 28 17:34:02 2010 -0800
+++ b/src/share/vm/code/codeCache.hpp	Wed Dec 29 10:41:43 2010 -0800
@@ -158,6 +158,7 @@
   static size_t  capacity()                      { return _heap->capacity(); }
   static size_t  max_capacity()                  { return _heap->max_capacity(); }
   static size_t  unallocated_capacity()          { return _heap->unallocated_capacity(); }
+  static size_t  largest_free_block()            { return _heap->largest_free_block(); }
   static bool    needs_flushing()                { return unallocated_capacity() < CodeCacheFlushingMinimumFreeSpace; }
 
   static bool needs_cache_clean()                { return _needs_cache_clean; }
--- a/src/share/vm/memory/heap.cpp	Tue Dec 28 17:34:02 2010 -0800
+++ b/src/share/vm/memory/heap.cpp	Wed Dec 29 10:41:43 2010 -0800
@@ -315,6 +315,15 @@
   return l;
 }
 
+size_t CodeHeap::largest_free_block() const {
+  size_t len = 0;
+  for (FreeBlock* b = _freelist; b != NULL; b = b->link()) {
+    if (b->length() > len)
+      len = b->length();
+  }
+  return size(len);
+}
+
 // Free list management
 
 FreeBlock *CodeHeap::following_block(FreeBlock *b) {
--- a/src/share/vm/memory/heap.hpp	Tue Dec 28 17:34:02 2010 -0800
+++ b/src/share/vm/memory/heap.hpp	Wed Dec 29 10:41:43 2010 -0800
@@ -161,6 +161,7 @@
   size_t max_capacity() const;
   size_t allocated_capacity() const;
   size_t unallocated_capacity() const            { return max_capacity() - allocated_capacity(); }
+  size_t largest_free_block() const;
 
   // Debugging
   void verify();
--- a/src/share/vm/opto/compile.cpp	Tue Dec 28 17:34:02 2010 -0800
+++ b/src/share/vm/opto/compile.cpp	Wed Dec 29 10:41:43 2010 -0800
@@ -444,22 +444,32 @@
 }
 
 
+//-----------------------init_scratch_buffer_blob------------------------------
+// Construct a temporary BufferBlob and cache it for this compile.
 void Compile::init_scratch_buffer_blob(int const_size) {
-  if (scratch_buffer_blob() != NULL)  return;
+  // If there is already a scratch buffer blob allocated and the
+  // constant section is big enough, use it.  Otherwise free the
+  // current and allocate a new one.
+  BufferBlob* blob = scratch_buffer_blob();
+  if ((blob != NULL) && (const_size <= _scratch_const_size)) {
+    // Use the current blob.
+  } else {
+    if (blob != NULL) {
+      BufferBlob::free(blob);
+    }
 
-  // Construct a temporary CodeBuffer to have it construct a BufferBlob
-  // Cache this BufferBlob for this compile.
-  ResourceMark rm;
-  _scratch_const_size = const_size;
-  int size = (MAX_inst_size + MAX_stubs_size + _scratch_const_size);
-  BufferBlob* blob = BufferBlob::create("Compile::scratch_buffer", size);
-  // Record the buffer blob for next time.
-  set_scratch_buffer_blob(blob);
-  // Have we run out of code space?
-  if (scratch_buffer_blob() == NULL) {
-    // Let CompilerBroker disable further compilations.
-    record_failure("Not enough space for scratch buffer in CodeCache");
-    return;
+    ResourceMark rm;
+    _scratch_const_size = const_size;
+    int size = (MAX_inst_size + MAX_stubs_size + _scratch_const_size);
+    blob = BufferBlob::create("Compile::scratch_buffer", size);
+    // Record the buffer blob for next time.
+    set_scratch_buffer_blob(blob);
+    // Have we run out of code space?
+    if (scratch_buffer_blob() == NULL) {
+      // Let CompilerBroker disable further compilations.
+      record_failure("Not enough space for scratch buffer in CodeCache");
+      return;
+    }
   }
 
   // Initialize the relocation buffers
@@ -468,13 +478,6 @@
 }
 
 
-void Compile::clear_scratch_buffer_blob() {
-  assert(scratch_buffer_blob(), "no BufferBlob set");
-  set_scratch_buffer_blob(NULL);
-  set_scratch_locs_memory(NULL);
-}
-
-
 //-----------------------scratch_emit_size-------------------------------------
 // Helper function that computes size by emitting code
 uint Compile::scratch_emit_size(const Node* n) {
--- a/src/share/vm/opto/output.cpp	Tue Dec 28 17:34:02 2010 -0800
+++ b/src/share/vm/opto/output.cpp	Wed Dec 29 10:41:43 2010 -0800
@@ -1746,9 +1746,6 @@
   // Walk backwards over each basic block, computing the needed alignment
   // Walk over all the basic blocks
   scheduling.DoScheduling();
-
-  // Clear the BufferBlob used for scheduling.
-  clear_scratch_buffer_blob();
 }
 
 //------------------------------ComputeLocalLatenciesForward-------------------