From 45f50032df5209fc224ebca8d51689d992164ab1 Mon Sep 17 00:00:00 2001 From: petermaxlee Date: Wed, 29 Jun 2016 16:02:48 -0700 Subject: [PATCH 1/2] [SPARK-16304] LinkageError should not crash Spark executor --- .../main/scala/org/apache/spark/executor/Executor.scala | 2 +- core/src/main/scala/org/apache/spark/util/Utils.scala | 6 ++++++ core/src/test/scala/org/apache/spark/FailureSuite.scala | 9 +++++++++ 3 files changed, 16 insertions(+), 1 deletion(-) diff --git a/core/src/main/scala/org/apache/spark/executor/Executor.scala b/core/src/main/scala/org/apache/spark/executor/Executor.scala index fbf2b86db1a2..fe749361609d 100644 --- a/core/src/main/scala/org/apache/spark/executor/Executor.scala +++ b/core/src/main/scala/org/apache/spark/executor/Executor.scala @@ -406,7 +406,7 @@ private[spark] class Executor( // Don't forcibly exit unless the exception was inherently fatal, to avoid // stopping other tasks unnecessarily. - if (Utils.isFatalError(t)) { + if (Utils.isFatalError(t) && !Utils.isLinkageError(t)) { SparkUncaughtExceptionHandler.uncaughtException(t) } diff --git a/core/src/main/scala/org/apache/spark/util/Utils.scala b/core/src/main/scala/org/apache/spark/util/Utils.scala index f77cc2f9b7aa..d3ea46206be5 100644 --- a/core/src/main/scala/org/apache/spark/util/Utils.scala +++ b/core/src/main/scala/org/apache/spark/util/Utils.scala @@ -1872,6 +1872,12 @@ private[spark] object Utils extends Logging { } } + /** Returns true if the given exception is a linkage error. */ + def isLinkageError(e: Throwable): Boolean = e match { + case _: java.lang.LinkageError => true + case _ => false + } + /** * Return a well-formed URI for the file described by a user input string. * diff --git a/core/src/test/scala/org/apache/spark/FailureSuite.scala b/core/src/test/scala/org/apache/spark/FailureSuite.scala index 132f6361e41e..d805c67714ff 100644 --- a/core/src/test/scala/org/apache/spark/FailureSuite.scala +++ b/core/src/test/scala/org/apache/spark/FailureSuite.scala @@ -253,6 +253,15 @@ class FailureSuite extends SparkFunSuite with LocalSparkContext { rdd.count() } + test("SPARK-16304: Link error should not crash executor") { + sc = new SparkContext("local[1,2]", "test") + intercept[SparkException] { + sc.parallelize(1 to 2).foreach { i => + throw new LinkageError() + } + } + } + // TODO: Need to add tests with shuffle fetch failures. } From 050e5247af0629f0ab7326842f1b45144777beba Mon Sep 17 00:00:00 2001 From: petermaxlee Date: Wed, 29 Jun 2016 23:56:20 -0700 Subject: [PATCH 2/2] code review --- .../scala/org/apache/spark/executor/Executor.scala | 2 +- .../src/main/scala/org/apache/spark/util/Utils.scala | 12 +++++------- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/core/src/main/scala/org/apache/spark/executor/Executor.scala b/core/src/main/scala/org/apache/spark/executor/Executor.scala index fe749361609d..fbf2b86db1a2 100644 --- a/core/src/main/scala/org/apache/spark/executor/Executor.scala +++ b/core/src/main/scala/org/apache/spark/executor/Executor.scala @@ -406,7 +406,7 @@ private[spark] class Executor( // Don't forcibly exit unless the exception was inherently fatal, to avoid // stopping other tasks unnecessarily. - if (Utils.isFatalError(t) && !Utils.isLinkageError(t)) { + if (Utils.isFatalError(t)) { SparkUncaughtExceptionHandler.uncaughtException(t) } diff --git a/core/src/main/scala/org/apache/spark/util/Utils.scala b/core/src/main/scala/org/apache/spark/util/Utils.scala index d3ea46206be5..b60066f0c4d8 100644 --- a/core/src/main/scala/org/apache/spark/util/Utils.scala +++ b/core/src/main/scala/org/apache/spark/util/Utils.scala @@ -1865,19 +1865,17 @@ private[spark] object Utils extends Logging { /** Returns true if the given exception was fatal. See docs for scala.util.control.NonFatal. */ def isFatalError(e: Throwable): Boolean = { e match { - case NonFatal(_) | _: InterruptedException | _: NotImplementedError | _: ControlThrowable => + case NonFatal(_) | + _: InterruptedException | + _: NotImplementedError | + _: ControlThrowable | + _: LinkageError => false case _ => true } } - /** Returns true if the given exception is a linkage error. */ - def isLinkageError(e: Throwable): Boolean = e match { - case _: java.lang.LinkageError => true - case _ => false - } - /** * Return a well-formed URI for the file described by a user input string. *