6969184: poor error recovery after symbol not found
authormcimadamore
Thu, 03 Feb 2011 09:37:28 +0000
changeset 8238 15ff254ff5c2
parent 8237 d5ef8db7ad09
child 8239 d2c934e951e2
6969184: poor error recovery after symbol not found Summary: generic type-well formedness check should ignore erroneous symbols Reviewed-by: jjg
langtools/src/share/classes/com/sun/tools/javac/comp/Check.java
langtools/test/tools/javac/generics/6969184/T6969184.java
langtools/test/tools/javac/generics/6969184/T6969184.out
--- a/langtools/src/share/classes/com/sun/tools/javac/comp/Check.java	Thu Feb 03 09:36:28 2011 +0000
+++ b/langtools/src/share/classes/com/sun/tools/javac/comp/Check.java	Thu Feb 03 09:37:28 2011 +0000
@@ -807,8 +807,9 @@
                 Type actual = types.subst(args.head,
                     type.tsym.type.getTypeArguments(),
                     tvars_buf.toList());
-                if (!checkExtends(actual, (TypeVar)tvars.head) &&
-                        !tvars.head.getUpperBound().isErroneous()) {
+                if (!isTypeArgErroneous(actual) &&
+                        !tvars.head.getUpperBound().isErroneous() &&
+                        !checkExtends(actual, (TypeVar)tvars.head)) {
                     return args.head;
                 }
                 args = args.tail;
@@ -821,14 +822,39 @@
             for (Type arg : types.capture(type).getTypeArguments()) {
                 if (arg.tag == TYPEVAR &&
                         arg.getUpperBound().isErroneous() &&
-                        !tvars.head.getUpperBound().isErroneous()) {
+                        !tvars.head.getUpperBound().isErroneous() &&
+                        !isTypeArgErroneous(args.head)) {
                     return args.head;
                 }
                 tvars = tvars.tail;
+                args = args.tail;
             }
 
             return null;
         }
+        //where
+        boolean isTypeArgErroneous(Type t) {
+            return isTypeArgErroneous.visit(t);
+        }
+
+        Types.UnaryVisitor<Boolean> isTypeArgErroneous = new Types.UnaryVisitor<Boolean>() {
+            public Boolean visitType(Type t, Void s) {
+                return t.isErroneous();
+            }
+            @Override
+            public Boolean visitTypeVar(TypeVar t, Void s) {
+                return visit(t.getUpperBound());
+            }
+            @Override
+            public Boolean visitCapturedType(CapturedType t, Void s) {
+                return visit(t.getUpperBound()) ||
+                        visit(t.getLowerBound());
+            }
+            @Override
+            public Boolean visitWildcardType(WildcardType t, Void s) {
+                return visit(t.type);
+            }
+        };
 
     /** Check that given modifiers are legal for given symbol and
      *  return modifiers together with any implicit modififiers for that symbol.
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/langtools/test/tools/javac/generics/6969184/T6969184.java	Thu Feb 03 09:37:28 2011 +0000
@@ -0,0 +1,29 @@
+/*
+ * @test /nodynamiccopyright/
+ * @bug 6956758
+ *
+ * @summary  poor error recovery after symbol not found
+ * @author Maurizio Cimadamore
+ * @compile/fail/ref=T6969184.out -XDrawDiagnostics T6969184.java
+ *
+ */
+
+class T6969184 {
+    static class C1<X> {
+        void m1(C1<? extends NonExistentClass> n) {}
+        void m2(C1<? super NonExistentClass> n) {}
+        void m3(C1<?> n) {}
+    }
+
+    static class C2<X extends NonExistentBound> {
+        void m1(C2<? extends NonExistentClass> n) {}
+        void m2(C2<? super NonExistentClass> n) {}
+        void m3(C2<?> n) {}
+    }
+
+    static class C3<X extends NonExistentBound1 & NonExistentBound2> {
+        void m1(C3<? extends NonExistentClass> n) {}
+        void m2(C3<? super NonExistentClass> n) {}
+        void m3(C3<?> n) {}
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/langtools/test/tools/javac/generics/6969184/T6969184.out	Thu Feb 03 09:37:28 2011 +0000
@@ -0,0 +1,10 @@
+T6969184.java:13:30: compiler.err.cant.resolve.location: kindname.class, NonExistentClass, , , (compiler.misc.location: kindname.class, T6969184.C1<X>, null)
+T6969184.java:14:28: compiler.err.cant.resolve.location: kindname.class, NonExistentClass, , , (compiler.misc.location: kindname.class, T6969184.C1<X>, null)
+T6969184.java:18:31: compiler.err.cant.resolve.location: kindname.class, NonExistentBound, , , (compiler.misc.location: kindname.class, T6969184, null)
+T6969184.java:19:30: compiler.err.cant.resolve.location: kindname.class, NonExistentClass, , , (compiler.misc.location: kindname.class, T6969184.C2<X>, null)
+T6969184.java:20:28: compiler.err.cant.resolve.location: kindname.class, NonExistentClass, , , (compiler.misc.location: kindname.class, T6969184.C2<X>, null)
+T6969184.java:24:31: compiler.err.cant.resolve.location: kindname.class, NonExistentBound1, , , (compiler.misc.location: kindname.class, T6969184, null)
+T6969184.java:24:51: compiler.err.cant.resolve.location: kindname.class, NonExistentBound2, , , (compiler.misc.location: kindname.class, T6969184, null)
+T6969184.java:25:30: compiler.err.cant.resolve.location: kindname.class, NonExistentClass, , , (compiler.misc.location: kindname.class, T6969184.C3<X>, null)
+T6969184.java:26:28: compiler.err.cant.resolve.location: kindname.class, NonExistentClass, , , (compiler.misc.location: kindname.class, T6969184.C3<X>, null)
+9 errors