Skip to content

Commit 182a26a

Browse files
committed
markFree of a constructor should never continue with the enclosing class
Previously there was a boundary condition where this could be the case for outermost classes.
1 parent a4e1546 commit 182a26a

File tree

1 file changed

+8
-7
lines changed

1 file changed

+8
-7
lines changed

compiler/src/dotty/tools/dotc/cc/CheckCaptures.scala

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -420,12 +420,9 @@ class CheckCaptures extends Recheck, SymTransformer:
420420

421421
/** The next environment enclosing `env` that needs to be charged
422422
* with free references.
423-
* @param included Whether an environment is included in the range of
424-
* environments to charge. Once `included` is false, no
425-
* more environments need to be charged.
426423
*/
427-
def nextEnvToCharge(env: Env, included: Env => Boolean)(using Context): Env =
428-
if env.owner.isConstructor && included(env.outer) then env.outer.outer
424+
def nextEnvToCharge(env: Env)(using Context): Env | Null =
425+
if env.owner.isConstructor then env.outer.outer0
429426
else env.outer
430427

431428
/** A description where this environment comes from */
@@ -535,7 +532,9 @@ class CheckCaptures extends Recheck, SymTransformer:
535532
checkSubset(included, env.captured, tree.srcPos, provenance(env))
536533
capt.println(i"Include call or box capture $included from $cs in ${env.owner} --> ${env.captured}")
537534
if !isOfNestedMethod(env) then
538-
recur(included, nextEnvToCharge(env, !_.owner.isStaticOwner), env)
535+
val nextEnv = nextEnvToCharge(env)
536+
if nextEnv != null && !nextEnv.owner.isStaticOwner then
537+
recur(included, nextEnv, env)
539538
// Under deferredReaches, don't propagate out of methods inside terms.
540539
// The use set of these methods will be charged when that method is called.
541540

@@ -2021,7 +2020,9 @@ class CheckCaptures extends Recheck, SymTransformer:
20212020
if env.kind == EnvKind.Boxed then env.owner
20222021
else if isOfNestedMethod(env) then env.owner.owner
20232022
else if env.owner.isStaticOwner then NoSymbol
2024-
else boxedOwner(nextEnvToCharge(env, alwaysTrue))
2023+
else
2024+
val nextEnv = nextEnvToCharge(env)
2025+
if nextEnv == null then NoSymbol else boxedOwner(nextEnv)
20252026

20262027
def checkUseUnlessBoxed(c: Capability, croot: NamedType) =
20272028
if !boxedOwner(env).isContainedIn(croot.symbol.owner) then

0 commit comments

Comments
 (0)