@@ -223,6 +223,22 @@ object CheckCaptures:
223
223
checkNotUniversal.traverse(tpe.widen)
224
224
end checkNotUniversalInUnboxedResult
225
225
226
+ trait CheckerAPI :
227
+ /** Complete symbol info of a val or a def */
228
+ def completeDef (tree : ValOrDefDef , sym : Symbol )(using Context ): Type
229
+
230
+ extension [T <: Tree ](tree : T )
231
+
232
+ /** Set new type of the tree if none was installed yet. */
233
+ def setNuType (tpe : Type ): Unit
234
+
235
+ /** The new type of the tree, or if none was installed, the original type */
236
+ def nuType (using Context ): Type
237
+
238
+ /** Was a new type installed for this tree? */
239
+ def hasNuType : Boolean
240
+ end CheckerAPI
241
+
226
242
class CheckCaptures extends Recheck , SymTransformer :
227
243
thisPhase =>
228
244
@@ -243,7 +259,7 @@ class CheckCaptures extends Recheck, SymTransformer:
243
259
244
260
val ccState1 = new CCState // Dotty problem: Rename to ccState ==> Crash in ExplicitOuter
245
261
246
- class CaptureChecker (ictx : Context ) extends Rechecker (ictx):
262
+ class CaptureChecker (ictx : Context ) extends Rechecker (ictx), CheckerAPI :
247
263
248
264
/** The current environment */
249
265
private val rootEnv : Env = inContext(ictx):
@@ -261,10 +277,6 @@ class CheckCaptures extends Recheck, SymTransformer:
261
277
*/
262
278
private val todoAtPostCheck = new mutable.ListBuffer [() => Unit ]
263
279
264
- override def keepType (tree : Tree ) =
265
- super .keepType(tree)
266
- || tree.isInstanceOf [Try ] // type of `try` needs tp be checked for * escapes
267
-
268
280
/** Instantiate capture set variables appearing contra-variantly to their
269
281
* upper approximation.
270
282
*/
@@ -286,8 +298,8 @@ class CheckCaptures extends Recheck, SymTransformer:
286
298
*/
287
299
private def interpolateVarsIn (tpt : Tree )(using Context ): Unit =
288
300
if tpt.isInstanceOf [InferredTypeTree ] then
289
- interpolator().traverse(tpt.knownType )
290
- .showing(i " solved vars in ${tpt.knownType }" , capt)
301
+ interpolator().traverse(tpt.nuType )
302
+ .showing(i " solved vars in ${tpt.nuType }" , capt)
291
303
for msg <- ccState.approxWarnings do
292
304
report.warning(msg, tpt.srcPos)
293
305
ccState.approxWarnings.clear()
@@ -501,11 +513,11 @@ class CheckCaptures extends Recheck, SymTransformer:
501
513
then (" \n This is often caused by a local capability$where\n leaking as part of its result." , fn.srcPos)
502
514
else if arg.span.exists then (" " , arg.srcPos)
503
515
else (" " , fn.srcPos)
504
- disallowRootCapabilitiesIn(arg.knownType , NoSymbol ,
516
+ disallowRootCapabilitiesIn(arg.nuType , NoSymbol ,
505
517
i " Type variable $pname of $sym" , " be instantiated to" , addendum, pos)
506
518
507
519
val param = fn.symbol.paramNamed(pname)
508
- if param.isUseParam then markFree(arg.knownType .deepCaptureSet, pos)
520
+ if param.isUseParam then markFree(arg.nuType .deepCaptureSet, pos)
509
521
end disallowCapInTypeArgs
510
522
511
523
override def recheckIdent (tree : Ident , pt : Type )(using Context ): Type =
@@ -769,8 +781,8 @@ class CheckCaptures extends Recheck, SymTransformer:
769
781
*/
770
782
def checkContains (tree : TypeApply )(using Context ): Unit = tree match
771
783
case ContainsImpl (csArg, refArg) =>
772
- val cs = csArg.knownType .captureSet
773
- val ref = refArg.knownType
784
+ val cs = csArg.nuType .captureSet
785
+ val ref = refArg.nuType
774
786
capt.println(i " check contains $cs , $ref" )
775
787
ref match
776
788
case ref : CaptureRef if ref.isTracked =>
@@ -852,7 +864,7 @@ class CheckCaptures extends Recheck, SymTransformer:
852
864
case _ =>
853
865
(sym, " " )
854
866
disallowRootCapabilitiesIn(
855
- tree.tpt.knownType , carrier, i " Mutable $sym" , " have type" , addendum, sym.srcPos)
867
+ tree.tpt.nuType , carrier, i " Mutable $sym" , " have type" , addendum, sym.srcPos)
856
868
checkInferredResult(super .recheckValDef(tree, sym), tree)
857
869
finally
858
870
if ! sym.is(Param ) then
@@ -1533,7 +1545,7 @@ class CheckCaptures extends Recheck, SymTransformer:
1533
1545
private val setup : SetupAPI = thisPhase.prev.asInstanceOf [Setup ]
1534
1546
1535
1547
override def checkUnit (unit : CompilationUnit )(using Context ): Unit =
1536
- setup.setupUnit(unit.tpdTree, completeDef )
1548
+ setup.setupUnit(unit.tpdTree, this )
1537
1549
collectCapturedMutVars.traverse(unit.tpdTree)
1538
1550
1539
1551
if ctx.settings.YccPrintSetup .value then
@@ -1676,7 +1688,7 @@ class CheckCaptures extends Recheck, SymTransformer:
1676
1688
traverseChildren(tp)
1677
1689
1678
1690
if tree.isInstanceOf [InferredTypeTree ] then
1679
- checker.traverse(tree.knownType )
1691
+ checker.traverse(tree.nuType )
1680
1692
end healTypeParam
1681
1693
1682
1694
/** Under the unsealed policy: Arrays are like vars, check that their element types
@@ -1716,10 +1728,10 @@ class CheckCaptures extends Recheck, SymTransformer:
1716
1728
check(tree)
1717
1729
def check (tree : Tree )(using Context ) = tree match
1718
1730
case TypeApply (fun, args) =>
1719
- fun.knownType .widen match
1731
+ fun.nuType .widen match
1720
1732
case tl : PolyType =>
1721
1733
val normArgs = args.lazyZip(tl.paramInfos).map: (arg, bounds) =>
1722
- arg.withType(arg.knownType .forceBoxStatus(
1734
+ arg.withType(arg.nuType .forceBoxStatus(
1723
1735
bounds.hi.isBoxedCapturing | bounds.lo.isBoxedCapturing))
1724
1736
checkBounds(normArgs, tl)
1725
1737
args.lazyZip(tl.paramNames).foreach(healTypeParam(_, _, fun.symbol))
@@ -1739,7 +1751,7 @@ class CheckCaptures extends Recheck, SymTransformer:
1739
1751
def traverse (t : Tree )(using Context ) = t match
1740
1752
case tree : InferredTypeTree =>
1741
1753
case tree : New =>
1742
- case tree : TypeTree => checkAppliedTypesIn(tree.withKnownType )
1754
+ case tree : TypeTree => checkAppliedTypesIn(tree.withType(tree.nuType) )
1743
1755
case _ => traverseChildren(t)
1744
1756
checkApplied.traverse(unit)
1745
1757
end postCheck
0 commit comments