Skip to content

Commit bc26c51

Browse files
committed
Delay roll-out of new prioritization scheme:
Now: 3.5: old scheme but warn if there are changes in the future 3.6-migration: new scheme, warn if prioritization has changed 3.6: new scheme, no warning
1 parent b644d30 commit bc26c51

File tree

9 files changed

+52
-20
lines changed

9 files changed

+52
-20
lines changed

compiler/src/dotty/tools/dotc/config/SourceVersion.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ enum SourceVersion:
1111
case `3.3-migration`, `3.3`
1212
case `3.4-migration`, `3.4`
1313
case `3.5-migration`, `3.5`
14+
case `3.6-migration`, `3.6`
1415
// !!! Keep in sync with scala.runtime.stdlibPatches.language !!!
1516
case `future-migration`, `future`
1617

compiler/src/dotty/tools/dotc/typer/Applications.scala

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1795,7 +1795,7 @@ trait Applications extends Compatibility {
17951795
* available in 3.0-migration if mode `Mode.OldImplicitResolution` is turned on as well.
17961796
* It is used to highlight differences between Scala 2 and 3 behavior.
17971797
*
1798-
* - In Scala 3.0-3.4, the behavior is as follows: `T <:p U` iff there is an impliit conversion
1798+
* - In Scala 3.0-3.5, the behavior is as follows: `T <:p U` iff there is an impliit conversion
17991799
* from `T` to `U`, or
18001800
*
18011801
* flip(T) <: flip(U)
@@ -1810,15 +1810,14 @@ trait Applications extends Compatibility {
18101810
* of parameters are not affected. So `T <: U` would imply `Set[Cmp[U]] <:p Set[Cmp[T]]`,
18111811
* as usual, because `Set` is non-variant.
18121812
*
1813-
* - From Scala 3.5, `T <:p U` means `T <: U` or `T` convertible to `U`
1813+
* - From Scala 3.6, `T <:p U` means `T <: U` or `T` convertible to `U`
18141814
* for overloading resolution (when `preferGeneral is false), and the opposite relation
18151815
* `U <: T` or `U convertible to `T` for implicit disambiguation between givens
18161816
* (when `preferGeneral` is true). For old-style implicit values, the 3.4 behavior is kept.
18171817
* If one of the alternatives is a given and the other is an implicit, the given wins.
18181818
*
1819-
* - In Scala 3.5-migration, use the 3.5 scheme normally, and the 3.4 scheme if
1820-
* `Mode.OldImplicitResolution` is on. This is used to highlight differences in the
1821-
* two resolution schemes.
1819+
* - In Scala 3.5 and Scala 3.6-migration, we issue a warning if the result under
1820+
* Scala 3.6 differ wrt to the old behavior up to 3.5.
18221821
*
18231822
* Also and only for given resolution: If a compared type refers to a given or its module class, use
18241823
* the intersection of its parent classes instead.
@@ -1844,8 +1843,8 @@ trait Applications extends Compatibility {
18441843
|| !alt1isGiven && !alt2isGiven
18451844
then
18461845
// Intermediate rules: better means specialize, but map all type arguments downwards
1847-
// These are enabled for 3.0-3.4, and for all comparisons between old-style implicits,
1848-
// and in 3.5-migration when we compare with previous rules.
1846+
// These are enabled for 3.0-3.5, and for all comparisons between old-style implicits,
1847+
// and in 3.5 amd 3.6-migration when we compare with previous rules.
18491848
val flip = new TypeMap:
18501849
def apply(t: Type) = t match
18511850
case t @ AppliedType(tycon, args) =>

compiler/src/dotty/tools/dotc/typer/Implicits.scala

Lines changed: 25 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1293,25 +1293,43 @@ trait Implicits:
12931293
* @return a number > 0 if `alt1` is preferred over `alt2`
12941294
* a number < 0 if `alt2` is preferred over `alt1`
12951295
* 0 if neither alternative is preferred over the other
1296+
* The behavior depends on the source version
1297+
* before 3.5: compare with preferGeneral = false
1298+
* 3.5: compare twice with preferGeneral = false and true, warning if result is different,
1299+
* return old result with preferGeneral = false
1300+
* 3.6-migration: compare twice with preferGeneral = false and true, warning if result is different,
1301+
* return new result with preferGeneral = true
1302+
* 3.6 and higher: compare with preferGeneral = true
1303+
*
12961304
*/
12971305
def compareAlternatives(alt1: RefAndLevel, alt2: RefAndLevel): Int =
12981306
def comp(using Context) = explore(compare(alt1.ref, alt2.ref, preferGeneral = true))
12991307
if alt1.ref eq alt2.ref then 0
13001308
else if alt1.level != alt2.level then alt1.level - alt2.level
13011309
else
1302-
val cmp = comp(using searchContext())
1303-
if Feature.sourceVersion == SourceVersion.`3.5-migration` then
1310+
var cmp = comp(using searchContext())
1311+
val sv = Feature.sourceVersion
1312+
if sv == SourceVersion.`3.5` || sv == SourceVersion.`3.6-migration` then
13041313
val prev = comp(using searchContext().addMode(Mode.OldImplicitResolution))
13051314
if cmp != prev then
13061315
def choice(c: Int) = c match
13071316
case -1 => "the second alternative"
13081317
case 1 => "the first alternative"
13091318
case _ => "none - it's ambiguous"
1310-
report.warning(
1311-
em"""Change in given search preference for $pt between alternatives ${alt1.ref} and ${alt2.ref}
1312-
|Previous choice: ${choice(prev)}
1313-
|New choice : ${choice(cmp)}""", srcPos)
1314-
cmp
1319+
if sv == SourceVersion.`3.5` then
1320+
report.warning(
1321+
em"""Given search preference for $pt between alternatives ${alt1.ref} and ${alt2.ref} will change
1322+
|Current choice : ${choice(prev)}
1323+
|New choice from Scala 3.6: ${choice(cmp)}""", srcPos)
1324+
prev
1325+
else
1326+
report.warning(
1327+
em"""Change in given search preference for $pt between alternatives ${alt1.ref} and ${alt2.ref}
1328+
|Previous choice : ${choice(prev)}
1329+
|New choice from Scala 3.6: ${choice(cmp)}""", srcPos)
1330+
cmp
1331+
else cmp
1332+
else cmp
13151333
end compareAlternatives
13161334

13171335
/** If `alt1` is also a search success, try to disambiguate as follows:

library/src/scala/runtime/stdLibPatches/language.scala

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -260,6 +260,20 @@ object language:
260260
@compileTimeOnly("`3.5` can only be used at compile time in import statements")
261261
object `3.5`
262262

263+
/** Set source version to 3.6-migration.
264+
*
265+
* @see [[https://docs.scala-lang.org/scala3/guides/migration/compatibility-intro.html]]
266+
*/
267+
@compileTimeOnly("`3.6-migration` can only be used at compile time in import statements")
268+
object `3.6-migration`
269+
270+
/** Set source version to 3.6
271+
*
272+
* @see [[https://docs.scala-lang.org/scala3/guides/migration/compatibility-intro.html]]
273+
*/
274+
@compileTimeOnly("`3.6` can only be used at compile time in import statements")
275+
object `3.6`
276+
263277
// !!! Keep in sync with dotty.tools.dotc.config.SourceVersion !!!
264278
// Also add tests in `tests/pos/source-import-3-x.scala` and `tests/pos/source-import-3-x-migration.scala`
265279

tests/neg/i15264.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import language.`3.5`
1+
import language.`3.6`
22
object priority:
33
// lower number = higher priority
44
class Prio0 extends Prio1

tests/run/implicit-specifity.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import language.`3.5`
1+
import language.`3.6`
22

33
case class Show[T](val i: Int)
44
object Show {

tests/run/implied-priority.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
/* These tests show various mechanisms available for implicit prioritization.
22
*/
3-
import language.`3.5`
3+
import language.`3.6`
44

55
class E[T](val str: String) // The type for which we infer terms below
66

tests/warn/given-triangle.check

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,5 +2,5 @@
22
16 |@main def Test = f // warn
33
| ^
44
| Change in given search preference for A between alternatives (given_A : A) and (given_B : B)
5-
| Previous choice: the second alternative
6-
| New choice : the first alternative
5+
| Previous choice : the second alternative
6+
| New choice from Scala 3.6: the first alternative

tests/warn/given-triangle.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
//> using options -source 3.5-migration
1+
//> using options -source 3.6-migration
22

33
class A
44
class B extends A

0 commit comments

Comments
 (0)