Skip to content

Instantly share code, notes, and snippets.

@headius
Created July 17, 2012 23:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save headius/3132731 to your computer and use it in GitHub Desktop.
Save headius/3132731 to your computer and use it in GitHub Desktop.
diff --git a/src/org/jruby/RubyThread.java b/src/org/jruby/RubyThread.java
index 99acb63..2aacd1d 100644
--- a/src/org/jruby/RubyThread.java
+++ b/src/org/jruby/RubyThread.java
@@ -73,6 +73,7 @@ import org.jruby.util.io.BlockingIO;
import org.jruby.util.io.SelectorFactory;
import org.jruby.util.log.Logger;
import org.jruby.util.log.LoggerFactory;
+import org.jruby.util.unsafe.UnsafeFactory;
import static org.jruby.CompatVersion.*;
@@ -1005,6 +1006,28 @@ public class RubyThread extends RubyObject implements ExecutionContext {
exitingException = exception;
}
+ /**
+ * For handling all non-Ruby exceptions bubbling out of threads
+ * @param exception
+ */
+ @SuppressWarnings("deprecation")
+ public void exceptionRaised(Throwable exception) {
+ if (exception instanceof RaiseException) {
+ exceptionRaised((RaiseException)exception);
+ }
+
+ assert isCurrent();
+
+ Ruby runtime = getRuntime();
+ if (abortOnException(runtime) && exception instanceof Error) {
+ // re-propagate on main thread
+ runtime.getThreadService().getMainThread().getNativeThread().stop(exception);
+ } else {
+ // just rethrow on this thread, let system handlers report it
+ UnsafeFactory.getUnsafe().throwException(exception);
+ }
+ }
+
private boolean abortOnException(Ruby runtime) {
return (runtime.isGlobalAbortOnExceptionEnabled() || abortOnException);
}
diff --git a/src/org/jruby/internal/runtime/RubyRunnable.java b/src/org/jruby/internal/runtime/RubyRunnable.java
index b26dc09..f65a634 100644
--- a/src/org/jruby/internal/runtime/RubyRunnable.java
+++ b/src/org/jruby/internal/runtime/RubyRunnable.java
@@ -27,14 +27,12 @@
***** END LICENSE BLOCK *****/
package org.jruby.internal.runtime;
-import org.jruby.Ruby;
-import org.jruby.RubyProc;
-import org.jruby.RubyThread;
-import org.jruby.RubyThreadGroup;
+import org.jruby.*;
import org.jruby.exceptions.JumpException;
import org.jruby.exceptions.MainExitException;
import org.jruby.exceptions.RaiseException;
import org.jruby.exceptions.ThreadKill;
+import org.jruby.javasupport.JavaUtil;
import org.jruby.runtime.Block;
import org.jruby.runtime.Frame;
import org.jruby.runtime.ThreadContext;
@@ -106,11 +104,11 @@ public class RubyRunnable implements Runnable {
} else {
rubyThread.exceptionRaised(runtime.newThreadError("return can't jump across threads"));
}
- } catch (RaiseException e) {
- rubyThread.exceptionRaised(e);
} catch (MainExitException mee) {
// Someone called exit!, so we need to kill the main thread
runtime.getThreadService().getMainThread().kill();
+ } catch (Throwable t) {
+ rubyThread.exceptionRaised(t);
} finally {
runtime.getThreadService().setCritical(false);
rubyThread.dispose();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment