summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/Implicits.scala2
-rw-r--r--src/library/scala/Predef.scala10
-rw-r--r--src/reflect/scala/reflect/internal/Definitions.scala3
-rw-r--r--src/reflect/scala/reflect/internal/StdNames.scala2
-rw-r--r--test/files/pos/t7788.scala8
5 files changed, 19 insertions, 6 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/Implicits.scala b/src/compiler/scala/tools/nsc/typechecker/Implicits.scala
index 8f5778862d..42687fa7b1 100644
--- a/src/compiler/scala/tools/nsc/typechecker/Implicits.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/Implicits.scala
@@ -807,7 +807,7 @@ trait Implicits {
private def isIneligible(info: ImplicitInfo) = (
info.isCyclicOrErroneous
- || isView && (info.sym eq Predef_conforms)
+ || isView && (info.sym eq Predef_conforms) // as an implicit conversion, Predef.$conforms is a no-op, so exclude it
|| (!context.macrosEnabled && info.sym.isTermMacro)
)
diff --git a/src/library/scala/Predef.scala b/src/library/scala/Predef.scala
index 2bde6795e0..faeb1dcbe2 100644
--- a/src/library/scala/Predef.scala
+++ b/src/library/scala/Predef.scala
@@ -382,9 +382,13 @@ object Predef extends LowPriorityImplicits with DeprecatedPredef {
@implicitNotFound(msg = "Cannot prove that ${From} <:< ${To}.")
sealed abstract class <:<[-From, +To] extends (From => To) with Serializable
private[this] final val singleton_<:< = new <:<[Any,Any] { def apply(x: Any): Any = x }
- // not in the <:< companion object because it is also
- // intended to subsume identity (which is no longer implicit)
- implicit def conforms[A]: A <:< A = singleton_<:<.asInstanceOf[A <:< A]
+ // The dollar prefix is to dodge accidental shadowing of this method
+ // by a user-defined method of the same name (SI-7788).
+ // The collections rely on this method.
+ implicit def $conforms[A]: A <:< A = singleton_<:<.asInstanceOf[A <:< A]
+
+ @deprecated("Use `implicitly[T <:< U]` or `identity` instead.", "2.11.0")
+ def conforms[A]: A <:< A = $conforms[A]
/** An instance of `A =:= B` witnesses that the types `A` and `B` are equal.
*
diff --git a/src/reflect/scala/reflect/internal/Definitions.scala b/src/reflect/scala/reflect/internal/Definitions.scala
index 645d6aa4ff..73f344345b 100644
--- a/src/reflect/scala/reflect/internal/Definitions.scala
+++ b/src/reflect/scala/reflect/internal/Definitions.scala
@@ -1429,7 +1429,8 @@ trait Definitions extends api.StandardDefinitions {
TypeTagClass -> materializeTypeTag
)
lazy val TagSymbols = TagMaterializers.keySet
- lazy val Predef_conforms = getMemberMethod(PredefModule, nme.conforms)
+ lazy val Predef_conforms = (getMemberIfDefined(PredefModule, nme.conforms)
+ orElse getMemberMethod(PredefModule, "conforms": TermName)) // TODO: predicate on -Xsource:2.10 (for now, needed for transition from M8 -> RC1)
lazy val Predef_classOf = getMemberMethod(PredefModule, nme.classOf)
lazy val Predef_implicitly = getMemberMethod(PredefModule, nme.implicitly)
lazy val Predef_wrapRefArray = getMemberMethod(PredefModule, nme.wrapRefArray)
diff --git a/src/reflect/scala/reflect/internal/StdNames.scala b/src/reflect/scala/reflect/internal/StdNames.scala
index aad5f32b5f..92245790cf 100644
--- a/src/reflect/scala/reflect/internal/StdNames.scala
+++ b/src/reflect/scala/reflect/internal/StdNames.scala
@@ -661,7 +661,7 @@ trait StdNames {
val classOf: NameType = "classOf"
val clone_ : NameType = "clone"
val collection: NameType = "collection"
- val conforms: NameType = "conforms"
+ val conforms: NameType = "$conforms" // dollar prefix to avoid accidental shadowing
val copy: NameType = "copy"
val create: NameType = "create"
val currentMirror: NameType = "currentMirror"
diff --git a/test/files/pos/t7788.scala b/test/files/pos/t7788.scala
new file mode 100644
index 0000000000..81eada962b
--- /dev/null
+++ b/test/files/pos/t7788.scala
@@ -0,0 +1,8 @@
+class Test {
+ // Predef used to define a method `conforms` to produce the implicit evidence below
+ // all this does is ensure we don't rename Predef.$conforms back to conforms when $ goes out of fashion
+ // or that there is some other way of generating the implicit value that witnesses T => U for T <: U
+ def conforms(x: Int, y: Int) = x < y
+ def foo[A](implicit ev: Int => A) = ???
+ foo[Int]
+} \ No newline at end of file