Improve error reporting inside of custom at-rules.

Patch by: bobv
Review by: rjrjr

git-svn-id: https://google-web-toolkit.googlecode.com/svn/trunk@6345 8db76d5a-ed1c-0410-87a9-c151d255dfc7
diff --git a/user/src/com/google/gwt/resources/css/GenerateCssAst.java b/user/src/com/google/gwt/resources/css/GenerateCssAst.java
index f9b37e4..ab0fe0e 100644
--- a/user/src/com/google/gwt/resources/css/GenerateCssAst.java
+++ b/user/src/com/google/gwt/resources/css/GenerateCssAst.java
@@ -110,6 +110,14 @@
       this.parentLogger = parentLogger;
     }
 
+    public TreeLogger branch(TreeLogger.Type type, String message) {
+      return branch(type, message, null);
+    }
+
+    public TreeLogger branch(TreeLogger.Type type, String message, Throwable t) {
+      return logOrBranch(type, message, t, true);
+    }
+
     public void error(CSSParseException exception) throws CSSException {
       // TODO Since this indicates a loss of data, should this be a fatal error?
       log(TreeLogger.WARN, exception);
@@ -124,11 +132,7 @@
     }
 
     public void log(TreeLogger.Type type, String message, Throwable t) {
-      fatalErrorEncountered |= type == TreeLogger.Type.ERROR;
-      if (parentLogger.isLoggable(type)) {
-        maybeBranch();
-        logger.log(type, message, t);
-      }
+      logOrBranch(type, message, t, false);
     }
 
     public void warning(CSSParseException exception) throws CSSException {
@@ -140,6 +144,22 @@
           + ": " + e.getMessage());
     }
 
+    private TreeLogger logOrBranch(TreeLogger.Type type, String message,
+        Throwable t, boolean branch) {
+      fatalErrorEncountered |= type == TreeLogger.Type.ERROR;
+      if (parentLogger.isLoggable(type)) {
+        maybeBranch();
+        if (branch) {
+          return logger.branch(type, message, t);
+        } else {
+          logger.log(type, message, t);
+          return null;
+        }
+      } else {
+        return TreeLogger.NULL;
+      }
+    }
+
     private void maybeBranch() {
       if (logger == null) {
         logger = parentLogger.branch(TreeLogger.INFO,
@@ -225,11 +245,21 @@
       } catch (IllegalAccessException e) {
         errors.log(TreeLogger.ERROR, "Unable to invoke parse method ", e);
       } catch (InvocationTargetException e) {
-        if (e.getCause() instanceof CSSException) {
-          throw (CSSException) e.getCause();
-        }
+        Throwable cause = e.getCause();
 
-        errors.log(TreeLogger.ERROR, "Unable to invoke parse method ", e);
+        if (cause instanceof CSSException) {
+          // Unwind a CSSException normally
+          throw (CSSException) cause;
+        } else if (cause != null) {
+          // Otherwise, report the message nicely
+          TreeLogger details = errors.branch(TreeLogger.ERROR,
+              cause.getMessage());
+          details.log(TreeLogger.DEBUG, "Full stack trace", cause);
+        } else {
+          TreeLogger details = errors.branch(TreeLogger.ERROR,
+              "Unknown failure parsing " + ruleName);
+          details.log(TreeLogger.DEBUG, "Full stack trace", e);
+        }
       }
     }