@@ -13,7 +13,7 @@ import Trees.*
1313import typer .RefChecks .{checkAllOverrides , checkSelfAgainstParents , OverridingPairsChecker }
1414import typer .Checking .{checkBounds , checkAppliedTypesIn }
1515import typer .ErrorReporting .{Addenda , NothingToAdd , err }
16- import typer .ProtoTypes .{AnySelectionProto , LhsProto }
16+ import typer .ProtoTypes .{LhsProto , WildcardSelectionProto }
1717import util .{SimpleIdentitySet , EqHashMap , EqHashSet , SrcPos , Property }
1818import transform .{Recheck , PreRecheck , CapturedVars }
1919import Recheck .*
@@ -183,6 +183,9 @@ object CheckCaptures:
183183 /** Attachment key for bodies of closures, provided they are values */
184184 val ClosureBodyValue = Property .Key [Unit ]
185185
186+ /** A prototype that indicates selection with an immutable value */
187+ class PathSelectionProto (val sym : Symbol , val pt : Type )(using Context ) extends WildcardSelectionProto
188+
186189class CheckCaptures extends Recheck , SymTransformer :
187190 thisPhase =>
188191
@@ -357,12 +360,13 @@ class CheckCaptures extends Recheck, SymTransformer:
357360 * the environment in which `sym` is defined.
358361 */
359362 def markFree (sym : Symbol , pos : SrcPos )(using Context ): Unit =
360- if sym.exists then
361- val ref = sym.termRef
362- if ref.isTracked then
363- forallOuterEnvsUpTo(sym.enclosure): env =>
364- capt.println(i " Mark $sym with cs ${ref.captureSet} free in ${env.owner}" )
365- checkElem(ref, env.captured, pos, provenance(env))
363+ markFree(sym, sym.termRef, pos)
364+
365+ def markFree (sym : Symbol , ref : TermRef , pos : SrcPos )(using Context ): Unit =
366+ if sym.exists && ref.isTracked then
367+ forallOuterEnvsUpTo(sym.enclosure): env =>
368+ capt.println(i " Mark $sym with cs ${ref.captureSet} free in ${env.owner}" )
369+ checkElem(ref, env.captured, pos, provenance(env))
366370
367371 /** Make sure (projected) `cs` is a subset of the capture sets of all enclosing
368372 * environments. At each stage, only include references from `cs` that are outside
@@ -464,9 +468,16 @@ class CheckCaptures extends Recheck, SymTransformer:
464468 includeCallCaptures(tree.symbol, tree.srcPos)
465469 else
466470 // debugShowEnvs()
467- markFree(tree.symbol, tree.srcPos)
471+ def addSelects (ref : TermRef , pt : Type ): TermRef = pt match
472+ case pt : PathSelectionProto => addSelects(ref.select(pt.sym).asInstanceOf [TermRef ], pt.pt)
473+ case _ => ref
474+ markFree(tree.symbol, addSelects(tree.symbol.termRef, pt), tree.srcPos)
468475 super .recheckIdent(tree, pt)
469476
477+ override def selectionProto (tree : Select , pt : Type )(using Context ): Type =
478+ if ! tree.symbol.isOneOf(UnstableValueFlags ) then PathSelectionProto (tree.symbol, pt)
479+ else super .selectionProto(tree, pt)
480+
470481 /** A specialized implementation of the selection rule.
471482 *
472483 * E |- f: T{ m: R^Cr }^{f}
0 commit comments