changeset 2253:494ed9fb8215

Fix stack leak in Shark This commit fixes a bug where having an exception handler in a loop would caused a little bit of stack to be allocated every time the handler was invoked. This code... int a = 23; int b = 0; while (true) { try { int c = a / b; } catch (ArithmeticException e) { // do nothing } } ...would eventually fail with a stack overflow. 2010-05-14 Gary Benson <gbenson@redhat.com> * ports/hotspot/src/share/vm/shark/sharkCodeBuffer.hpp (SharkCodeBuffer::inline_data): New method. * ports/hotspot/src/share/vm/shark/sharkBuilder.hpp (SharkBuilder::CreateInlineData): Likewise. * ports/hotspot/src/share/vm/shark/sharkBuilder.cpp (SharkBuilder::CreateInlineData): Likewise. * ports/hotspot/src/share/vm/shark/sharkTopLevelBlock.cpp (SharkTopLevelBlock::handle_exception): Inline the exception handler table in the code buffer rather than creating it on the stack.
author Gary Benson <gbenson@redhat.com>
date Fri, 14 May 2010 17:37:29 +0100
parents 254a1f83b7da
children d7d97061baf3
files ChangeLog ports/hotspot/src/share/vm/shark/sharkBuilder.cpp ports/hotspot/src/share/vm/shark/sharkBuilder.hpp ports/hotspot/src/share/vm/shark/sharkCodeBuffer.hpp ports/hotspot/src/share/vm/shark/sharkTopLevelBlock.cpp
diffstat 5 files changed, 42 insertions(+), 10 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Fri May 14 13:55:26 2010 +0100
+++ b/ChangeLog	Fri May 14 17:37:29 2010 +0100
@@ -1,3 +1,16 @@
+2010-05-14  Gary Benson  <gbenson@redhat.com>
+
+	* ports/hotspot/src/share/vm/shark/sharkCodeBuffer.hpp
+	(SharkCodeBuffer::inline_data): New method.
+	* ports/hotspot/src/share/vm/shark/sharkBuilder.hpp
+	(SharkBuilder::CreateInlineData): Likewise.
+	* ports/hotspot/src/share/vm/shark/sharkBuilder.cpp
+	(SharkBuilder::CreateInlineData): Likewise.
+	* ports/hotspot/src/share/vm/shark/sharkTopLevelBlock.cpp
+	(SharkTopLevelBlock::handle_exception): Inline the exception
+	handler table in the code buffer rather than creating it on
+	the stack.
+
 2010-05-14  Gary Benson  <gbenson@redhat.com>
 
 	PR icedtea/484
--- a/ports/hotspot/src/share/vm/shark/sharkBuilder.cpp	Fri May 14 13:55:26 2010 +0100
+++ b/ports/hotspot/src/share/vm/shark/sharkBuilder.cpp	Fri May 14 17:37:29 2010 +0100
@@ -546,6 +546,16 @@
     name);
 }
 
+Value* SharkBuilder::CreateInlineData(void*       data,
+                                      size_t      size,
+                                      const Type* type, 
+                                      const char* name) {
+  return CreateIntToPtr(
+    code_buffer_address(code_buffer()->inline_data(data, size)),
+    type,
+    name);
+}
+
 // Helpers for creating basic blocks.
 
 BasicBlock* SharkBuilder::GetBlockInsertionPoint() const {
--- a/ports/hotspot/src/share/vm/shark/sharkBuilder.hpp	Fri May 14 13:55:26 2010 +0100
+++ b/ports/hotspot/src/share/vm/shark/sharkBuilder.hpp	Fri May 14 17:37:29 2010 +0100
@@ -194,6 +194,10 @@
   llvm::Value* CreateInlineOop(ciObject* object, const char* name = "") {
     return CreateInlineOop(object->encoding(), name);
   }
+  llvm::Value* CreateInlineData(void*             data,
+                                size_t            size,
+                                const llvm::Type* type, 
+                                const char*       name = ""); 
 
   // Helpers for creating basic blocks.
   // NB don't use unless SharkFunction::CreateBlock is unavailable.
--- a/ports/hotspot/src/share/vm/shark/sharkCodeBuffer.hpp	Fri May 14 13:55:26 2010 +0100
+++ b/ports/hotspot/src/share/vm/shark/sharkCodeBuffer.hpp	Fri May 14 17:37:29 2010 +0100
@@ -73,4 +73,15 @@
     masm()->store_oop(object);
     return offset;
   }
+
+  // Inline a block of non-oop data into the buffer and return its offset.
+ public:
+  int inline_data(void *src, size_t size) const {
+    masm()->align(BytesPerWord);
+    int offset = masm()->offset();
+    void *dst = masm()->pc();
+    masm()->advance(size);
+    memcpy(dst, src, size);
+    return offset;
+  }
 };
--- a/ports/hotspot/src/share/vm/shark/sharkTopLevelBlock.cpp	Fri May 14 13:55:26 2010 +0100
+++ b/ports/hotspot/src/share/vm/shark/sharkTopLevelBlock.cpp	Fri May 14 17:37:29 2010 +0100
@@ -469,18 +469,12 @@
 
     // Drop into the runtime if there are non-catch-all options
     if (num_options > 0) {
-      Value *options = builder()->CreateAlloca(
-        ArrayType::get(SharkType::jint_type(), num_options),
-        LLVMValue::jint_constant(1));
-
-      for (int i = 0; i < num_options; i++)
-        builder()->CreateStore(
-          LLVMValue::jint_constant(indexes[i]),
-          builder()->CreateStructGEP(options, i));
-
       Value *index = call_vm(
         builder()->find_exception_handler(),
-        builder()->CreateStructGEP(options, 0),
+        builder()->CreateInlineData(
+          indexes,
+          num_options * sizeof(int),
+          PointerType::getUnqual(SharkType::jint_type())),
         LLVMValue::jint_constant(num_options),
         EX_CHECK_NO_CATCH);