Skip to content

Commit 9d8e2bc

Browse files
committed
Make captureRoot an element of caps
This avoids the problem that we do not want to make `*` visible under the scala package, even if pureFunctions or captureChecking is enabled.
1 parent f1574fa commit 9d8e2bc

File tree

25 files changed

+48
-38
lines changed

25 files changed

+48
-38
lines changed

compiler/src/dotty/tools/dotc/ast/TreeInfo.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -408,10 +408,10 @@ trait UntypedTreeInfo extends TreeInfo[Untyped] { self: Trees.Instance[Untyped]
408408

409409
def apply(tp: ByNameTypeTree)(using Context): untpd.CapturingTypeTree =
410410
untpd.CapturingTypeTree(
411-
Ident(nme.CAPTURE_ROOT).withSpan(tp.span.startPos) :: Nil, tp)
411+
untpd.captureRoot.withSpan(tp.span.startPos) :: Nil, tp)
412412

413413
def unapply(tp: Tree)(using Context): Option[ByNameTypeTree] = tp match
414-
case untpd.CapturingTypeTree(id @ Ident(nme.CAPTURE_ROOT) :: Nil, bntp: ByNameTypeTree)
414+
case untpd.CapturingTypeTree(id @ Select(_, nme.CAPTURE_ROOT) :: Nil, bntp: ByNameTypeTree)
415415
if id.span == bntp.span.startPos => Some(bntp)
416416
case _ => None
417417
end ImpureByNameTypeTree

compiler/src/dotty/tools/dotc/ast/untpd.scala

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -492,6 +492,9 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo {
492492
def scalaAny(implicit src: SourceFile): Select = scalaDot(tpnme.Any)
493493
def javaDotLangDot(name: Name)(implicit src: SourceFile): Select = Select(Select(Ident(nme.java), nme.lang), name)
494494

495+
def captureRoot(using Context): Select =
496+
Select(scalaDot(nme.caps), nme.CAPTURE_ROOT)
497+
495498
def makeConstructor(tparams: List[TypeDef], vparamss: List[List[ValDef]], rhs: Tree = EmptyTree)(using Context): DefDef =
496499
DefDef(nme.CONSTRUCTOR, joinParams(tparams, vparamss), TypeTree(), rhs)
497500

compiler/src/dotty/tools/dotc/core/Definitions.scala

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -470,7 +470,6 @@ class Definitions {
470470

471471
@tu lazy val andType: TypeSymbol = enterBinaryAlias(tpnme.AND, AndType(_, _))
472472
@tu lazy val orType: TypeSymbol = enterBinaryAlias(tpnme.OR, OrType(_, _, soft = false))
473-
@tu lazy val captureRoot: TermSymbol = enterPermanentSymbol(nme.CAPTURE_ROOT, AnyType).asTerm
474473

475474
/** Method representing a throw */
476475
@tu lazy val throwMethod: TermSymbol = enterMethod(OpsPackageClass, nme.THROWkw,
@@ -964,6 +963,7 @@ class Definitions {
964963
@tu lazy val CapsModule: Symbol = requiredModule("scala.caps")
965964
@tu lazy val Caps_unsafeBox: Symbol = CapsModule.requiredMethod("unsafeBox")
966965
@tu lazy val Caps_unsafeUnbox: Symbol = CapsModule.requiredMethod("unsafeUnbox")
966+
@tu lazy val captureRoot: TermSymbol = CapsModule.requiredValue("*")
967967

968968
// Annotation base classes
969969
@tu lazy val AnnotationClass: ClassSymbol = requiredClass("scala.annotation.Annotation")
@@ -1984,9 +1984,8 @@ class Definitions {
19841984
this.initCtx = ctx
19851985
if (!isInitialized) {
19861986
// force initialization of every symbol that is synthesized or hijacked by the compiler
1987-
val forced = syntheticCoreClasses ++ syntheticCoreMethods ++ ScalaValueClasses()
1988-
++ (JavaEnumClass :: (if Feature.ccEnabled then captureRoot :: Nil else Nil))
1989-
1987+
val forced =
1988+
syntheticCoreClasses ++ syntheticCoreMethods ++ ScalaValueClasses() :+ JavaEnumClass
19901989
isInitialized = true
19911990
}
19921991
addSyntheticSymbolsComments

compiler/src/dotty/tools/dotc/core/StdNames.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -425,6 +425,7 @@ object StdNames {
425425
val bytes: N = "bytes"
426426
val canEqual_ : N = "canEqual"
427427
val canEqualAny : N = "canEqualAny"
428+
val caps: N = "caps"
428429
val checkInitialized: N = "checkInitialized"
429430
val classOf: N = "classOf"
430431
val classType: N = "classType"

compiler/src/dotty/tools/dotc/parsing/Parsers.scala

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -159,7 +159,7 @@ object Parsers {
159159
syntaxError(msg.toMessage, span)
160160

161161
def unimplementedExpr(using Context): Select =
162-
Select(Select(rootDot(nme.scala), nme.Predef), nme.???)
162+
Select(scalaDot(nme.Predef), nme.???)
163163
}
164164

165165
trait OutlineParserCommon extends ParserCommon {
@@ -1444,7 +1444,10 @@ object Parsers {
14441444
/** CaptureRef ::= ident | `this`
14451445
*/
14461446
def captureRef(): Tree =
1447-
if in.token == THIS then simpleRef() else termIdent()
1447+
if in.token == THIS then simpleRef()
1448+
else termIdent() match
1449+
case Ident(nme.CAPTURE_ROOT) => captureRoot
1450+
case id => id
14481451

14491452
/** CaptureSet ::= `{` CaptureRef {`,` CaptureRef} `}` -- under captureChecking
14501453
*/

compiler/src/dotty/tools/dotc/printing/PlainPrinter.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -376,6 +376,7 @@ class PlainPrinter(_ctx: Context) extends Printer {
376376

377377
def toTextCaptureRef(tp: Type): Text =
378378
homogenize(tp) match
379+
case tp: TermRef if tp.symbol == defn.captureRoot => Str("*")
379380
case tp: SingletonType => toTextRef(tp)
380381
case _ => toText(tp)
381382

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

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2682,7 +2682,7 @@ class Typer(@constructorOnly nestingLevel: Int = 0) extends Namer
26822682
val arg1 = typed(tree.arg, pt)
26832683
if (ctx.mode is Mode.Type) {
26842684
val cls = annot1.symbol.maybeOwner
2685-
if ctx.settings.Ycc.value
2685+
if Feature.ccEnabled
26862686
&& (cls == defn.RetainsAnnot || cls == defn.RetainsByNameAnnot)
26872687
then
26882688
CheckCaptures.checkWellformed(annot1)

library/src/scala/caps.scala

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,9 @@ import annotation.experimental
55
@experimental
66
object caps:
77

8+
/** The universal capture reference */
9+
val `*`: Any = ()
10+
811
/** If argument is of type `cs T`, converts to type `box cs T`. This
912
* avoids the error that would be raised when boxing `*`.
1013
*/

tests/disabled/neg-custom-args/captures/capt-wf.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
// No longer valid
22
class C
3-
type Cap = C @retains(*)
4-
type Top = Any @retains(*)
3+
type Cap = C @retains(caps.*)
4+
type Top = Any @retains(caps.*)
55

66
type T = (x: Cap) => List[String @retains(x)] => Unit // error
77
val x: (x: Cap) => Array[String @retains(x)] = ??? // error

tests/disabled/neg-custom-args/captures/try2.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import annotation.ability
55
@ability erased val canThrow: * = ???
66

77
class CanThrow[E <: Exception] extends Retains[canThrow.type]
8-
type Top = Any @retains(*)
8+
type Top = Any @retains(caps.*)
99

1010
infix type throws[R, E <: Exception] = (erased CanThrow[E]) ?=> R
1111

tests/neg-custom-args/captures/capt-depfun.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import annotation.retains
22
class C
3-
type Cap = C @retains(*)
3+
type Cap = C @retains(caps.*)
44

55
def f(y: Cap, z: Cap) =
66
def g(): C @retains(y, z) = ???

tests/neg-custom-args/captures/capt-depfun2.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import annotation.retains
22
class C
3-
type Cap = C @retains(*)
3+
type Cap = C @retains(caps.*)
44

55
def f(y: Cap, z: Cap) =
66
def g(): C @retains(y, z) = ???

tests/neg-custom-args/captures/capt-test.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@ import annotation.retains
22
import language.experimental.erasedDefinitions
33

44
class CT[E <: Exception]
5-
type CanThrow[E <: Exception] = CT[E] @retains(*)
6-
type Top = Any @retains(*)
5+
type CanThrow[E <: Exception] = CT[E] @retains(caps.*)
6+
type Top = Any @retains(caps.*)
77

88
infix type throws[R, E <: Exception] = (erased CanThrow[E]) ?=> R
99

tests/neg-custom-args/captures/capt1.scala

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,21 @@
11
import annotation.retains
22
class C
3-
def f(x: C @retains(*), y: C): () -> C =
3+
def f(x: C @retains(caps.*), y: C): () -> C =
44
() => if x == null then y else y // error
55

6-
def g(x: C @retains(*), y: C): Matchable =
6+
def g(x: C @retains(caps.*), y: C): Matchable =
77
() => if x == null then y else y // error
88

9-
def h1(x: C @retains(*), y: C): Any =
9+
def h1(x: C @retains(caps.*), y: C): Any =
1010
def f() = if x == null then y else y
1111
() => f() // ok
1212

13-
def h2(x: C @retains(*)): Matchable =
13+
def h2(x: C @retains(caps.*)): Matchable =
1414
def f(y: Int) = if x == null then y else y // error
1515
f
1616

1717
class A
18-
type Cap = C @retains(*)
18+
type Cap = C @retains(caps.*)
1919

2020
def h3(x: Cap): A =
2121
class F(y: Int) extends A: // error
@@ -27,7 +27,7 @@ def h4(x: Cap, y: Int): A =
2727
def m() = if x == null then y else y
2828

2929
def foo() =
30-
val x: C @retains(*) = ???
30+
val x: C @retains(caps.*) = ???
3131
def h[X](a: X)(b: X) = a
3232
val z2 = h[() -> Cap](() => x) // error
3333
(() => C()) // error

tests/neg-custom-args/captures/capt3.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import annotation.retains
22
class C
3-
type Cap = C @retains(*)
3+
type Cap = C @retains(caps.*)
44

55
def test1() =
66
val x: Cap = C()
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import annotation.retains
22
object Test:
33

4-
def f[A <: Matchable @retains(*)](x: A): Matchable = x // error
4+
def f[A <: Matchable @retains(caps.*)](x: A): Matchable = x // error
55

tests/neg-custom-args/captures/io.scala

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,17 +3,17 @@ sealed trait IO:
33
def puts(msg: Any): Unit = println(msg)
44

55
def test1 =
6-
val IO : IO @retains(*) = new IO {}
6+
val IO : IO @retains(caps.*) = new IO {}
77
def foo = {IO; IO.puts("hello") }
88
val x : () -> Unit = () => foo // error: Found: (() -> Unit) retains IO; Required: () -> Unit
99

1010
def test2 =
11-
val IO : IO @retains(*) = new IO {}
12-
def puts(msg: Any, io: IO @retains(*)) = println(msg)
11+
val IO : IO @retains(caps.*) = new IO {}
12+
def puts(msg: Any, io: IO @retains(caps.*)) = println(msg)
1313
def foo() = puts("hello", IO)
1414
val x : () -> Unit = () => foo() // error: Found: (() -> Unit) retains IO; Required: () -> Unit
1515

16-
type Capability[T] = T @retains(*)
16+
type Capability[T] = T @retains(caps.*)
1717

1818
def test3 =
1919
val IO : Capability[IO] = new IO {}

tests/neg-custom-args/captures/try.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@ import annotation.retains
22
import language.experimental.erasedDefinitions
33

44
class CT[E <: Exception]
5-
type CanThrow[E <: Exception] = CT[E] @retains(*)
6-
type Top = Any @retains(*)
5+
type CanThrow[E <: Exception] = CT[E] @retains(caps.*)
6+
type Top = Any @retains(caps.*)
77

88
infix type throws[R, E <: Exception] = (erased CanThrow[E]) ?=> R
99

tests/pos-custom-args/captures/boxmap.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import annotation.retains
2-
type Top = Any @retains(*)
2+
type Top = Any @retains(caps.*)
33

44
type Box[+T <: Top] = ([K <: Top] -> (T => K) -> K)
55

tests/pos-custom-args/captures/capt-depfun.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
import annotation.retains
22
class C
3-
type Cap = C @retains(*)
3+
type Cap = C @retains(caps.*)
44

55
type T = (x: Cap) -> String @retains(x)
66

77
type ID[X] = X
88

99
val aa: ((x: Cap) -> String @retains(x)) = (x: Cap) => ""
1010

11-
def f(y: Cap, z: Cap): String @retains(*) =
11+
def f(y: Cap, z: Cap): String @retains(caps.*) =
1212
val a: ((x: Cap) -> String @retains(x)) = (x: Cap) => ""
1313
val b = a(y)
1414
val c: String @retains(y) = b

tests/pos-custom-args/captures/capt-depfun2.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import annotation.retains
22
class C
3-
type Cap = C @retains(*)
3+
type Cap = C @retains(caps.*)
44

55
def f(y: Cap, z: Cap) =
66
def g(): C @retains(y, z) = ???

tests/pos-custom-args/captures/capt0.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,5 @@ object Test:
33
def test() =
44
val x: {*} Any = "abc"
55
val y: Object @scala.annotation.retains(x) = ???
6-
val z: Object @scala.annotation.retains(x, *) = y: Object @annotation.retains(x)
6+
val z: Object @scala.annotation.retains(x, caps.*) = y: Object @annotation.retains(x)
77

tests/pos-custom-args/captures/capt2.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import annotation.retains
22
class C
3-
type Cap = C @retains(*)
3+
type Cap = C @retains(caps.*)
44

55
def test1() =
66
val y: {*} String = ""

tests/pos-custom-args/captures/cc-expand.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ object Test:
55
class B
66
class C
77
class CTC
8-
type CT = CTC @retains(*)
8+
type CT = CTC @retains(caps.*)
99

1010
def test(ct: CT, dt: CT) =
1111

tests/pos-custom-args/captures/try.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import annotation.retains
22
import language.experimental.erasedDefinitions
33

44
class CT[E <: Exception]
5-
type CanThrow[E <: Exception] = CT[E] @retains(*)
5+
type CanThrow[E <: Exception] = CT[E] @retains(caps.*)
66

77
infix type throws[R, E <: Exception] = (erased CanThrow[E]) ?-> R
88

0 commit comments

Comments
 (0)