Permalink
Browse files

SI-7232 Fix Java import vs defn. binding precendence

Java Spec:
> A single-type-import declaration d in a compilation unit c
> of package p that imports a type named n shadows, throughout
> c, the declarations of:
>   - any top level type named n declared in another compilation
>     unit of p
>   - any type named n imported by a type-import-on-demand
>     declaration in c
>   - any type named n imported by a static-import-on-demand
>     declaration in c

Scala Spec:
> Bindings of different kinds have a precedence defined on them:
>   1. Definitions and declarations that are local, inherited, or made
>      available by a package clause in the same compilation unit where
>      the definition occurs have highest precedence.
>   2. Explicit imports have next highest precedence.

This is a forward port of 6e79370, which did not merge cleanly
and was omitted in the regular merge from 2.10.x to master.

Conflicts:
	src/compiler/scala/tools/nsc/typechecker/Typers.scala
  • Loading branch information...
1 parent 59d4998 commit 8383b65fb53ae9424cf9c6f1314ee73321ad3b9a @retronym retronym committed Mar 11, 2013
@@ -912,7 +912,25 @@ trait Contexts { self: Analyzer =>
def lookupImport(imp: ImportInfo, requireExplicit: Boolean) =
importedAccessibleSymbol(imp, name, requireExplicit) filter qualifies
- while (!impSym.exists && imports.nonEmpty && imp1.depth > symbolDepth) {
+ // Java: A single-type-import declaration d in a compilation unit c of package p
+ // that imports a type named n shadows, throughout c, the declarations of:
+ //
+ // 1) any top level type named n declared in another compilation unit of p
+ //
+ // A type-import-on-demand declaration never causes any other declaration to be shadowed.
+ //
+ // Scala: Bindings of different kinds have a precedence defined on them:
+ //
+ // 1) Definitions and declarations that are local, inherited, or made available by a
+ // package clause in the same compilation unit where the definition occurs have
+ // highest precedence.
+ // 2) Explicit imports have next highest precedence.
+ def depthOk(imp: ImportInfo) = (
+ imp.depth > symbolDepth
+ || (unit.isJava && imp.isExplicitImport(name) && imp.depth == symbolDepth)
+ )
+
+ while (!impSym.exists && imports.nonEmpty && depthOk(imports.head)) {
impSym = lookupImport(imp1, requireExplicit = false)
if (!impSym.exists)
imports = imports.tail
@@ -530,7 +530,13 @@ trait Namers extends MethodSynthesis {
// Setting the position at the import means that if there is
// more than one hidden name, the second will not be warned.
// So it is the position of the actual hidden name.
- checkNotRedundant(tree.pos withPoint fromPos, from, to)
+ //
+ // Note: java imports have precence over definitions in the same package
+ // so don't warn for them. There is a corresponding special treatment
+ // in the shadowing rules in typedIdent to (SI-7232). In any case,
+ // we shouldn't be emitting warnings for .java source files.
+ if (!context.unit.isJava)
+ checkNotRedundant(tree.pos withPoint fromPos, from, to)
}
}
@@ -0,0 +1 @@
+-Xfatal-warnings
@@ -0,0 +1,9 @@
+package pack;
+
+import java.util.List;
+
+public class Foo {
+ public static java.util.List okay() { throw new Error(); }
+
+ public static List wrong() { throw new Error(); }
+}
@@ -0,0 +1,4 @@
+package pack;
+
+public class List {
+}
@@ -0,0 +1,5 @@
+object Test {
+ import pack._
+ Foo.okay().size()
+ Foo.wrong().size()
+}
@@ -0,0 +1 @@
+-Xfatal-warnings
@@ -0,0 +1,8 @@
+package pack;
+
+import java.util.*;
+
+public class Foo {
+ // should be pack.List.
+ public static List list() { throw new Error(); }
+}
@@ -0,0 +1,5 @@
+package pack;
+
+public class List {
+ public void packList() {}
+}
@@ -0,0 +1,5 @@
+object Test {
+ import pack._
+
+ Foo.list().packList()
+}
@@ -0,0 +1 @@
+-Xfatal-warnings
@@ -0,0 +1,10 @@
+package pack;
+
+import java.util.List;
+
+public class Foo {
+ public static class List {
+ public void isInnerList() {}
+ }
+ public static List innerList() { throw new Error(); }
+}
@@ -0,0 +1,4 @@
+object Test {
+ import pack._
+ Foo.innerList().isInnerList()
+}
@@ -0,0 +1 @@
+-Xfatal-warnings
@@ -0,0 +1,4 @@
+package pack;
+
+public class Entry {
+}
@@ -0,0 +1,8 @@
+package pack;
+
+import java.util.Map.Entry;
+
+public class Foo {
+ public static Entry mapEntry() { throw new Error(); }
+ public static void javaTest() { mapEntry().getKey(); }
+}
@@ -0,0 +1,4 @@
+object Test {
+ import pack._
+ Foo.mapEntry().getKey()
+}

0 comments on commit 8383b65

Please sign in to comment.