@@ -63,7 +63,7 @@ class Semantic {
63
63
/** An object with unknown initialization status */
64
64
case object Cold extends Value
65
65
66
- sealed abstract class Addr extends Value {
66
+ sealed abstract class Ref extends Value {
67
67
def klass : ClassSymbol
68
68
def outer : Value
69
69
def objekt : Objekt
@@ -84,7 +84,7 @@ class Semantic {
84
84
}
85
85
86
86
/** A reference to the object under initialization pointed by `this` */
87
- case class ThisRef (klass : ClassSymbol , outer : Value , ctor : Symbol , args : List [Value ]) extends Addr {
87
+ case class ThisRef (klass : ClassSymbol , outer : Value , ctor : Symbol , args : List [Value ]) extends Ref {
88
88
/** Caches initialized fields */
89
89
val objekt = Objekt (klass, fields = mutable.Map .empty, outers = mutable.Map (klass -> outer))
90
90
}
@@ -93,7 +93,7 @@ class Semantic {
93
93
*
94
94
* We need to restrict nesting levels of `outer` to finitize the domain.
95
95
*/
96
- case class Warm (klass : ClassSymbol , outer : Value , args : List [Value ]) extends Addr {
96
+ case class Warm (klass : ClassSymbol , outer : Value , args : List [Value ]) extends Ref {
97
97
val objekt = getCachedObject()
98
98
99
99
private def getCachedObject () =
@@ -106,13 +106,13 @@ class Semantic {
106
106
}
107
107
108
108
/** A function value */
109
- case class Fun (expr : Tree , thisV : Addr , klass : ClassSymbol , env : Env ) extends Value
109
+ case class Fun (expr : Tree , thisV : Ref , klass : ClassSymbol , env : Env ) extends Value
110
110
111
111
/** A value which represents a set of addresses
112
112
*
113
113
* It comes from `if` expressions.
114
114
*/
115
- case class RefSet (refs : List [Fun | Addr ]) extends Value
115
+ case class RefSet (refs : List [Fun | Ref ]) extends Value
116
116
117
117
// end of value definition
118
118
@@ -152,10 +152,10 @@ class Semantic {
152
152
def empty : Heap = mutable.Map .empty
153
153
154
154
extension (heap : Heap )
155
- def contains (addr : Warm ): Boolean = heap.contains(addr )
156
- def apply (addr : Warm ): Objekt = heap(addr )
157
- def update (addr : Warm , obj : Objekt ): Unit =
158
- heap(addr ) = obj
155
+ def contains (ref : Warm ): Boolean = heap.contains(ref )
156
+ def apply (ref : Warm ): Objekt = heap(ref )
157
+ def update (ref : Warm , obj : Objekt ): Unit =
158
+ heap(ref ) = obj
159
159
end extension
160
160
}
161
161
type Heap = Heap .Heap
@@ -331,7 +331,7 @@ class Semantic {
331
331
/** Conservatively approximate the value with `Cold` or `Hot` */
332
332
def widenArg : Value =
333
333
a match
334
- case _ : Addr | _ : Fun => Cold
334
+ case _ : Ref | _ : Fun => Cold
335
335
case RefSet (refs) => refs.map(_.widenArg).join
336
336
case _ => a
337
337
@@ -354,18 +354,18 @@ class Semantic {
354
354
val error = AccessCold (field, source, trace.toVector)
355
355
Result (Hot , error :: Nil )
356
356
357
- case addr : Addr =>
358
- val target = if needResolve then resolve(addr .klass, field) else field
357
+ case ref : Ref =>
358
+ val target = if needResolve then resolve(ref .klass, field) else field
359
359
val trace1 = trace.add(source)
360
360
if target.is(Flags .Lazy ) then
361
361
given Trace = trace1
362
362
val rhs = target.defTree.asInstanceOf [ValDef ].rhs
363
- eval(rhs, addr , target.owner.asClass, cacheResult = true )
363
+ eval(rhs, ref , target.owner.asClass, cacheResult = true )
364
364
else
365
- val obj = addr .objekt
365
+ val obj = ref .objekt
366
366
if obj.hasField(target) then
367
367
Result (obj.field(target), Nil )
368
- else if addr .isInstanceOf [Warm ] then
368
+ else if ref .isInstanceOf [Warm ] then
369
369
if target.is(Flags .ParamAccessor ) then
370
370
// possible for trait parameters
371
371
// see tests/init/neg/trait2.scala
@@ -374,7 +374,7 @@ class Semantic {
374
374
Result (Hot , Nil )
375
375
else if target.hasSource then
376
376
val rhs = target.defTree.asInstanceOf [ValOrDefDef ].rhs
377
- eval(rhs, addr , target.owner.asClass, cacheResult = true )
377
+ eval(rhs, ref , target.owner.asClass, cacheResult = true )
378
378
else
379
379
val error = CallUnknown (field, source, trace.toVector)
380
380
Result (Hot , error :: Nil )
@@ -407,15 +407,15 @@ class Semantic {
407
407
val error = CallCold (meth, source, trace.toVector)
408
408
Result (Hot , error :: checkArgs)
409
409
410
- case addr : Addr =>
410
+ case ref : Ref =>
411
411
val isLocal = ! meth.owner.isClass
412
412
val target =
413
413
if ! needResolve then
414
414
meth
415
415
else if superType.exists then
416
- resolveSuper(addr .klass, superType, meth)
416
+ resolveSuper(ref .klass, superType, meth)
417
417
else
418
- resolve(addr .klass, meth)
418
+ resolve(ref .klass, meth)
419
419
420
420
if target.isOneOf(Flags .Method ) then
421
421
val trace1 = trace.add(source)
@@ -427,25 +427,25 @@ class Semantic {
427
427
if target.isPrimaryConstructor then
428
428
given Env = env2
429
429
val tpl = cls.defTree.asInstanceOf [TypeDef ].rhs.asInstanceOf [Template ]
430
- val res = withTrace(trace.add(cls.defTree)) { eval(tpl, addr , cls, cacheResult = true ) }
431
- Result (addr , res.errors)
430
+ val res = withTrace(trace.add(cls.defTree)) { eval(tpl, ref , cls, cacheResult = true ) }
431
+ Result (ref , res.errors)
432
432
else if target.isConstructor then
433
433
given Env = env2
434
- eval(ddef.rhs, addr , cls, cacheResult = true )
434
+ eval(ddef.rhs, ref , cls, cacheResult = true )
435
435
else
436
436
// normal method call
437
437
withEnv(if isLocal then env else Env .empty) {
438
- eval(ddef.rhs, addr , cls, cacheResult = true ) ++ checkArgs
438
+ eval(ddef.rhs, ref , cls, cacheResult = true ) ++ checkArgs
439
439
}
440
- else if addr .canIgnoreMethodCall(target) then
440
+ else if ref .canIgnoreMethodCall(target) then
441
441
Result (Hot , Nil )
442
442
else
443
443
// no source code available
444
444
val error = CallUnknown (target, source, trace.toVector)
445
445
Result (Hot , error :: checkArgs)
446
446
else
447
447
// method call resolves to a field
448
- val obj = addr .objekt
448
+ val obj = ref .objekt
449
449
if obj.hasField(target) then
450
450
Result (obj.field(target), Nil )
451
451
else
@@ -494,12 +494,12 @@ class Semantic {
494
494
val error = CallCold (ctor, source, trace1.toVector)
495
495
Result (Hot , error :: Nil )
496
496
497
- case addr : Addr =>
497
+ case ref : Ref =>
498
498
given Trace = trace1
499
499
// widen the outer to finitize addresses
500
- val outer = addr match
500
+ val outer = ref match
501
501
case Warm (_, _ : Warm , _) => Cold
502
- case _ => addr
502
+ case _ => ref
503
503
504
504
val argsWidened = args.map(_.value).widenArgs
505
505
val value = Warm (klass, outer, argsWidened)
@@ -549,7 +549,7 @@ class Semantic {
549
549
550
550
case Cold => Result (Cold , Nil )
551
551
552
- case addr : Addr => eval(vdef.rhs, addr , klass)
552
+ case ref : Ref => eval(vdef.rhs, ref , klass)
553
553
554
554
case _ =>
555
555
report.error(" unexpected defTree when accessing local variable, sym = " + sym.show + " , defTree = " + sym.defTree.show, source)
@@ -561,7 +561,7 @@ class Semantic {
561
561
end extension
562
562
563
563
// ----- Promotion ----------------------------------------------------
564
- extension (addr : Addr )
564
+ extension (ref : Ref )
565
565
/** Whether the object is fully assigned
566
566
*
567
567
* It means all fields and outers are set. For performance, we don't check
@@ -572,9 +572,9 @@ class Semantic {
572
572
* object freely, as its fields or outers may still reach uninitialized
573
573
* objects.
574
574
*/
575
- def isFullyFilled : Contextual [Boolean ] = log(" isFullyFilled " + addr , printer) {
576
- val obj = addr .objekt
577
- addr .klass.baseClasses.forall { klass =>
575
+ def isFullyFilled : Contextual [Boolean ] = log(" isFullyFilled " + ref , printer) {
576
+ val obj = ref .objekt
577
+ ref .klass.baseClasses.forall { klass =>
578
578
! klass.hasSource || {
579
579
val nonInits = klass.info.decls.filter { member =>
580
580
! member.isOneOf(Flags .Method | Flags .Lazy | Flags .Deferred )
@@ -690,7 +690,7 @@ class Semantic {
690
690
end extension
691
691
692
692
// ----- Policies ------------------------------------------------------
693
- extension (value : Addr )
693
+ extension (value : Ref )
694
694
/** Can the method call on `value` be ignored?
695
695
*
696
696
* Note: assume overriding resolution has been performed.
@@ -713,7 +713,7 @@ class Semantic {
713
713
714
714
/** Process the worklist until done */
715
715
@ tailrec
716
- def work ()(using Context ): Unit =
716
+ final def work ()(using Context ): Unit =
717
717
pendingTasks match
718
718
case task :: rest =>
719
719
pendingTasks = rest
@@ -769,7 +769,7 @@ class Semantic {
769
769
*
770
770
* This method only handles cache logic and delegates the work to `cases`.
771
771
*/
772
- def eval (expr : Tree , thisV : Addr , klass : ClassSymbol , cacheResult : Boolean = false ): Contextual [Result ] = log(" evaluating " + expr.show + " , this = " + thisV.show, printer, (_ : Result ).show) {
772
+ def eval (expr : Tree , thisV : Ref , klass : ClassSymbol , cacheResult : Boolean = false ): Contextual [Result ] = log(" evaluating " + expr.show + " , this = " + thisV.show, printer, (_ : Result ).show) {
773
773
val innerMap = cache.getOrElseUpdate(thisV, new EqHashMap [Tree , Value ])
774
774
if (innerMap.contains(expr)) Result (innerMap(expr), Errors .empty)
775
775
else {
@@ -785,11 +785,11 @@ class Semantic {
785
785
}
786
786
787
787
/** Evaluate a list of expressions */
788
- def eval (exprs : List [Tree ], thisV : Addr , klass : ClassSymbol ): Contextual [List [Result ]] =
788
+ def eval (exprs : List [Tree ], thisV : Ref , klass : ClassSymbol ): Contextual [List [Result ]] =
789
789
exprs.map { expr => eval(expr, thisV, klass) }
790
790
791
791
/** Evaluate arguments of methods */
792
- def evalArgs (args : List [Arg ], thisV : Addr , klass : ClassSymbol ): Contextual [(List [Error ], List [ArgInfo ])] =
792
+ def evalArgs (args : List [Arg ], thisV : Ref , klass : ClassSymbol ): Contextual [(List [Error ], List [ArgInfo ])] =
793
793
val errors = new mutable.ArrayBuffer [Error ]
794
794
val argInfos = new mutable.ArrayBuffer [ArgInfo ]
795
795
args.foreach { arg =>
@@ -809,7 +809,7 @@ class Semantic {
809
809
*
810
810
* Note: Recursive call should go to `eval` instead of `cases`.
811
811
*/
812
- def cases (expr : Tree , thisV : Addr , klass : ClassSymbol ): Contextual [Result ] =
812
+ def cases (expr : Tree , thisV : Ref , klass : ClassSymbol ): Contextual [Result ] =
813
813
expr match {
814
814
case Ident (nme.WILDCARD ) =>
815
815
// TODO: disallow `var x: T = _`
@@ -975,7 +975,7 @@ class Semantic {
975
975
}
976
976
977
977
/** Handle semantics of leaf nodes */
978
- def cases (tp : Type , thisV : Addr , klass : ClassSymbol , source : Tree ): Contextual [Result ] = log(" evaluating " + tp.show, printer, (_ : Result ).show) {
978
+ def cases (tp : Type , thisV : Ref , klass : ClassSymbol , source : Tree ): Contextual [Result ] = log(" evaluating " + tp.show, printer, (_ : Result ).show) {
979
979
tp match {
980
980
case _ : ConstantType =>
981
981
Result (Hot , Errors .empty)
@@ -1044,8 +1044,8 @@ class Semantic {
1044
1044
thisV match
1045
1045
case Hot => Hot
1046
1046
1047
- case addr : Addr =>
1048
- val obj = addr .objekt
1047
+ case ref : Ref =>
1048
+ val obj = ref .objekt
1049
1049
val curOpt = obj.klass.baseClasses.find(cls => reachable(cls, hops))
1050
1050
curOpt match
1051
1051
case Some (cur) =>
@@ -1066,7 +1066,7 @@ class Semantic {
1066
1066
}
1067
1067
1068
1068
/** Compute the outer value that correspond to `tref.prefix` */
1069
- def outerValue (tref : TypeRef , thisV : Addr , klass : ClassSymbol , source : Tree ): Contextual [Result ] =
1069
+ def outerValue (tref : TypeRef , thisV : Ref , klass : ClassSymbol , source : Tree ): Contextual [Result ] =
1070
1070
val cls = tref.classSymbol.asClass
1071
1071
if tref.prefix == NoPrefix then
1072
1072
val enclosing = cls.owner.lexicallyEnclosingClass.asClass
@@ -1197,7 +1197,7 @@ class Semantic {
1197
1197
*
1198
1198
* This is intended to avoid type soundness issues in Dotty.
1199
1199
*/
1200
- def checkTermUsage (tpt : Tree , thisV : Addr , klass : ClassSymbol ): Contextual [List [Error ]] =
1200
+ def checkTermUsage (tpt : Tree , thisV : Ref , klass : ClassSymbol ): Contextual [List [Error ]] =
1201
1201
val buf = new mutable.ArrayBuffer [Error ]
1202
1202
val traverser = new TypeTraverser {
1203
1203
def traverse (tp : Type ): Unit = tp match {
0 commit comments