Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorStephan Herrmann2013-02-22 18:48:36 +0000
committerJayaprakash Arthanareeswaran2013-04-03 09:02:14 +0000
commit7f149cbd31a29082f285cf448e823f215f36990d (patch)
treec16cbb92231cbfc21b4686b4868c7adf131f64f7
parent43e6a1aaf95a700a23727644400d8055e7261c91 (diff)
downloadeclipse.jdt.core-7f149cbd31a29082f285cf448e823f215f36990d.tar.gz
eclipse.jdt.core-7f149cbd31a29082f285cf448e823f215f36990d.tar.xz
eclipse.jdt.core-7f149cbd31a29082f285cf448e823f215f36990d.zip
Bug 401456 - Code compiles from javac/intellij, but fails from eclipse
-rw-r--r--org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericTypeTest.java7
-rw-r--r--org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericsRegressionTest.java42
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/Scope.java37
3 files changed, 74 insertions, 12 deletions
diff --git a/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericTypeTest.java b/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericTypeTest.java
index 1b1042d2b6..f83ec1fab9 100644
--- a/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericTypeTest.java
+++ b/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericTypeTest.java
@@ -38788,8 +38788,7 @@ public void test1132() {
" X myThing = new X<Object>();\n" +
" Integer i = myThing.getList().get(0); // Type Mismatch error - Since\n" +
" // myThing is unbounded, return\n" +
- " // type List<Integer>\n" +
- " // incorrectly becomes unbounded\n" +
+ " // type List<Integer> becomes unbounded\n" +
" }\n" +
"\n" +
" public List<Integer> getList() {\n" +
@@ -38821,12 +38820,12 @@ public void test1132() {
" ^^^^^^^^^^^^^^^^^^^^^^^^\n" +
"Type mismatch: cannot convert from Object to Integer\n" +
"----------\n" +
- "3. WARNING in X.java (at line 25)\n" +
+ "3. WARNING in X.java (at line 24)\n" +
" X myThing = new X<Object>();\n" +
" ^\n" +
"X is a raw type. References to generic type X<T> should be parameterized\n" +
"----------\n" +
- "4. WARNING in X.java (at line 26)\n" +
+ "4. WARNING in X.java (at line 25)\n" +
" List<Integer> l = myThing.getList();\n" +
" ^^^^^^^^^^^^^^^^^\n" +
"Type safety: The expression of type List needs unchecked conversion to conform to List<Integer>\n" +
diff --git a/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericsRegressionTest.java b/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericsRegressionTest.java
index 8721046913..6b769ebdf7 100644
--- a/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericsRegressionTest.java
+++ b/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericsRegressionTest.java
@@ -10,6 +10,7 @@
* Stephan Herrmann <stephan@cs.tu-berlin.de> - Contributions for
* bug 282152 - [1.5][compiler] Generics code rejected by Eclipse but accepted by javac
* bug 395002 - Self bound generic class doesn't resolve bounds properly for wildcards for certain parametrisation.
+ * bug 401456 - Code compiles from javac/intellij, but fails from eclipse
*******************************************************************************/
package org.eclipse.jdt.core.tests.compiler.regression;
@@ -30,7 +31,7 @@ public class GenericsRegressionTest extends AbstractComparableTest {
// Static initializer to specify tests subset using TESTS_* static variables
// All specified tests which does not belong to the class are skipped...
static {
-// TESTS_NAMES = new String[] { "testBug395002_combined" };
+// TESTS_NAMES = new String[] { "test401456" };
// TESTS_NAMES = new String[] { "test1464" };
// TESTS_NUMBERS = new int[] { 1465 };
// TESTS_RANGE = new int[] { 1097, -1 };
@@ -2817,4 +2818,43 @@ public void test397888b() {
"----------\n",
null, true, customOptions);
}
+// Bug 401456 - Code compiles from javac/intellij, but fails from eclipse
+public void test401456() {
+ runConformTest(
+ new String[] {
+ "App.java",
+ "import java.util.List;\n" +
+ "\n" +
+ "public class App {\n" +
+ "\n" +
+ " public interface Command_1<T> {\n" +
+ " public void execute(T o);\n" +
+ " }\n" +
+ " public static class ObservableEventWithArg<T> {\n" +
+ " public class Monitor {\n" +
+ " public Object addListener(final Command_1<T> l) {\n" +
+ " return null;\n" +
+ " }\n" +
+ " }\n" +
+ " }\n" +
+ " public static class Context<T> {\n" +
+ " public ObservableEventWithArg<String>.Monitor getSubmissionErrorEventMonitor() {\n" +
+ " return new ObservableEventWithArg<String>().new Monitor();\n" +
+ " }\n" +
+ " }\n" +
+ "\n" +
+ " public static void main(String[] args) {\n" +
+ " compileError(new Context<List<String>>());\n" +
+ " }\n" +
+ "\n" +
+ " private static void compileError(Context context) {\n" +
+ " context.getSubmissionErrorEventMonitor().addListener(\n" + // here the inner message send bogusly resolved to ObservableEventWithArg#RAW.Monitor
+ " new Command_1<String>() {\n" +
+ " public void execute(String o) {\n" +
+ " }\n" +
+ " });\n" +
+ " }\n" +
+ "}\n"
+ });
+}
} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/Scope.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/Scope.java
index 641d61fc6e..80a1b6a431 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/Scope.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/Scope.java
@@ -15,8 +15,12 @@
* bug 186342 - [compiler][null] Using annotations for null checking
* bug 387612 - Unreachable catch block...exception is never thrown from the try
* bug 395002 - Self bound generic class doesn't resolve bounds properly for wildcards for certain parametrisation.
+<<<<<<< BETA_JAVA8
* Jesper S Moller - Contributions for
* bug 382721 - [1.8][compiler] Effectively final variables needs special treatment
+=======
+ * bug 401456 - Code compiles from javac/intellij, but fails from eclipse
+>>>>>>> 8200b6c Bug 401456 - Code compiles from javac/intellij, but fails from eclipse
*******************************************************************************/
package org.eclipse.jdt.internal.compiler.lookup;
@@ -359,13 +363,12 @@ public abstract class Scope {
/**
* Returns a type, where original type was substituted using the receiver
* parameterized type.
- * In raw mode, all parameterized type denoting same original type are converted
- * to raw types. e.g.
- * class X <T> {
- * X<T> foo;
- * X<String> bar;
- * } when used in raw fashion, then type of both foo and bar is raw type X.
- *
+ * In raw mode (see {@link Substitution#isRawSubstitution()}),
+ * all parameterized types are converted to raw types.
+ * Cf. 4.8: "The type of a constructor (8.8), instance method (8.4, 9.4),
+ * or non-static field (8.3) M of a raw type C that is not inherited from its
+ * superclasses or superinterfaces is the raw type that corresponds to the erasure
+ * of its type in the generic declaration corresponding to C."
*/
public static TypeBinding substitute(Substitution substitution, TypeBinding originalType) {
if (originalType == null) return null;
@@ -380,6 +383,9 @@ public abstract class Scope {
ReferenceBinding substitutedEnclosing = originalEnclosing;
if (originalEnclosing != null) {
substitutedEnclosing = (ReferenceBinding) substitute(substitution, originalEnclosing);
+ if (isMemberTypeOfRaw(originalType, substitutedEnclosing))
+ return originalParameterizedType.environment.createRawType(
+ originalParameterizedType.genericType(), substitutedEnclosing);
}
TypeBinding[] originalArguments = originalParameterizedType.arguments;
TypeBinding[] substitutedArguments = originalArguments;
@@ -443,6 +449,8 @@ public abstract class Scope {
substitutedEnclosing = originalEnclosing;
if (originalEnclosing != null) {
substitutedEnclosing = (ReferenceBinding) substitute(substitution, originalEnclosing);
+ if (isMemberTypeOfRaw(originalType, substitutedEnclosing))
+ return substitution.environment().createRawType(originalReferenceType, substitutedEnclosing);
}
// treat as if parameterized with its type variables (non generic type gets 'null' arguments)
@@ -458,6 +466,8 @@ public abstract class Scope {
substitutedEnclosing = originalEnclosing;
if (originalEnclosing != null) {
substitutedEnclosing = (ReferenceBinding) substitute(substitution, originalEnclosing);
+ if (isMemberTypeOfRaw(originalType, substitutedEnclosing))
+ return substitution.environment().createRawType(originalReferenceType, substitutedEnclosing);
}
if (substitution.isRawSubstitution()) {
@@ -471,6 +481,19 @@ public abstract class Scope {
return originalType;
}
+ private static boolean isMemberTypeOfRaw(TypeBinding originalType, ReferenceBinding substitutedEnclosing) {
+ // 4.8:
+ // "a raw type is defined to be one of:
+ // ...
+ // * A non-static member type of a raw type R that is not
+ // inherited from a superclass or superinterface of R."
+
+ // Due to staticness, e.g., Map.Entry<String,Object> is *not* considered as a raw type
+
+ return (substitutedEnclosing != null && substitutedEnclosing.isRawType())
+ && ((originalType instanceof ReferenceBinding) && !((ReferenceBinding)originalType).isStatic());
+ }
+
/**
* Returns an array of types, where original types got substituted given a substitution.
* Only allocate an array if anything is different.

Back to the top