Ensures that EvalExceptionWithStackTrace does not have an empty exception message.

--
MOS_MIGRATED_REVID=101659996
diff --git a/src/main/java/com/google/devtools/build/lib/syntax/EvalExceptionWithStackTrace.java b/src/main/java/com/google/devtools/build/lib/syntax/EvalExceptionWithStackTrace.java
index d967962..d1baabc 100644
--- a/src/main/java/com/google/devtools/build/lib/syntax/EvalExceptionWithStackTrace.java
+++ b/src/main/java/com/google/devtools/build/lib/syntax/EvalExceptionWithStackTrace.java
@@ -30,7 +30,7 @@
   private StackTraceElement mostRecentElement;
 
   public EvalExceptionWithStackTrace(Exception original, Location callLocation) {
-    super(callLocation, original.getMessage(), original.getCause());
+    super(callLocation, getNonEmptyMessage(original), original.getCause());
   }
 
   /**
@@ -215,4 +215,33 @@
       output.addLast(message);
     }
   }
+
+  /**
+   * Returns a non-empty message for the given exception.
+   *
+   * <p> If the exception itself does not have a message, a new message is constructed from the
+   * exception's class name.
+   * For example, an IllegalArgumentException will lead to "Illegal Argument".
+   */
+  private static String getNonEmptyMessage(Exception original) {
+    Preconditions.checkNotNull(original);
+    String msg = original.getMessage();
+    if (msg != null && !msg.isEmpty()) {
+      return msg;
+    }
+
+    char[] name = original.getClass().getSimpleName().replace("Exception", "").toCharArray();
+    boolean first = true;
+    StringBuilder builder = new StringBuilder();
+
+    for (char current : name) {
+      if (Character.isUpperCase(current) && !first) {
+        builder.append(" ");
+      }
+      builder.append(current);
+      first = false;
+    }
+
+    return builder.toString();
+  }
 }