@@ -17,6 +17,8 @@ import dotty.tools.dotc.transform.MegaPhase.MiniPhase
17
17
import dotty .tools .dotc .transform .ValueClasses
18
18
19
19
private class ResolveReflectEval (config : ExpressionCompilerConfig , expressionStore : ExpressionStore ) extends MiniPhase :
20
+ private val reflectEvalName = termName(" reflectEval" )
21
+ private val elemName = termName(" elem" )
20
22
override def phaseName : String = ResolveReflectEval .name
21
23
22
24
override def transformTypeDef (tree : TypeDef )(using Context ): Tree =
@@ -29,7 +31,7 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
29
31
// unbox the result of the `evaluate` method if it is a value class
30
32
val gen = new Gen (
31
33
Apply (
32
- Select (This (config.expressionClass), termName( " reflectEval " ) ),
34
+ Select (This (config.expressionClass), reflectEvalName ),
33
35
List (nullLiteral, nullLiteral, nullLiteral)
34
36
)
35
37
)
@@ -44,25 +46,28 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
44
46
case ReflectEvalStrategy .This (cls) => gen.getThisObject
45
47
case ReflectEvalStrategy .LocalOuter (cls) => gen.getLocalValue(" $outer" )
46
48
case ReflectEvalStrategy .Outer (outerCls) => gen.getOuter(qualifier, outerCls)
49
+
47
50
case ReflectEvalStrategy .LocalValue (variable, isByName) =>
48
51
val variableName = JavaEncoding .encode(variable.name)
49
52
val rawLocalValue = gen.getLocalValue(variableName)
50
53
val localValue = if isByName then gen.evaluateByName(rawLocalValue) else rawLocalValue
51
54
val derefLocalValue = gen.derefCapturedVar(localValue, variable)
52
55
gen.boxIfValueClass(variable, derefLocalValue)
56
+
53
57
case ReflectEvalStrategy .LocalValueAssign (variable) =>
54
58
val value = gen.unboxIfValueClass(variable, args.head)
55
59
val typeSymbol = variable.info.typeSymbol.asType
56
60
val variableName = JavaEncoding .encode(variable.name)
57
61
JavaEncoding .encode(typeSymbol) match
58
62
case s " scala.runtime. ${_}Ref " =>
59
- val elemField = typeSymbol.info.decl(termName( " elem " ) ).symbol
63
+ val elemField = typeSymbol.info.decl(elemName ).symbol
60
64
gen.setField(tree)(
61
65
gen.getLocalValue(variableName),
62
66
elemField.asTerm,
63
67
value
64
68
)
65
69
case _ => gen.setLocalValue(variableName, value)
70
+
66
71
case ReflectEvalStrategy .ClassCapture (variable, cls, isByName) =>
67
72
val rawCapture = gen
68
73
.getClassCapture(tree)(qualifier, variable.name, cls)
@@ -73,6 +78,7 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
73
78
val capture = if isByName then gen.evaluateByName(rawCapture) else rawCapture
74
79
val capturedValue = gen.derefCapturedVar(capture, variable)
75
80
gen.boxIfValueClass(variable, capturedValue)
81
+
76
82
case ReflectEvalStrategy .ClassCaptureAssign (variable, cls) =>
77
83
val capture = gen
78
84
.getClassCapture(tree)(qualifier, variable.name, cls)
@@ -82,8 +88,9 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
82
88
}
83
89
val value = gen.unboxIfValueClass(variable, args.head)
84
90
val typeSymbol = variable.info.typeSymbol
85
- val elemField = typeSymbol.info.decl(termName( " elem " ) ).symbol
91
+ val elemField = typeSymbol.info.decl(elemName ).symbol
86
92
gen.setField(tree)(capture, elemField.asTerm, value)
93
+
87
94
case ReflectEvalStrategy .MethodCapture (variable, method, isByName) =>
88
95
val rawCapture = gen
89
96
.getMethodCapture(method, variable.name)
@@ -94,6 +101,7 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
94
101
val capture = if isByName then gen.evaluateByName(rawCapture) else rawCapture
95
102
val capturedValue = gen.derefCapturedVar(capture, variable)
96
103
gen.boxIfValueClass(variable, capturedValue)
104
+
97
105
case ReflectEvalStrategy .MethodCaptureAssign (variable, method) =>
98
106
val capture = gen
99
107
.getMethodCapture(method, variable.name)
@@ -103,9 +111,11 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
103
111
}
104
112
val value = gen.unboxIfValueClass(variable, args.head)
105
113
val typeSymbol = variable.info.typeSymbol
106
- val elemField = typeSymbol.info.decl(termName( " elem " ) ).symbol
114
+ val elemField = typeSymbol.info.decl(elemName ).symbol
107
115
gen.setField(tree)(capture, elemField.asTerm, value)
116
+
108
117
case ReflectEvalStrategy .StaticObject (obj) => gen.getStaticObject(obj)
118
+
109
119
case ReflectEvalStrategy .Field (field, isByName) =>
110
120
// if the field is lazy, if it is private in a value class or a trait
111
121
// then we must call the getter method
@@ -116,17 +126,19 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
116
126
val rawValue = gen.getField(tree)(qualifier, field)
117
127
if isByName then gen.evaluateByName(rawValue) else rawValue
118
128
gen.boxIfValueClass(field, fieldValue)
129
+
119
130
case ReflectEvalStrategy .FieldAssign (field) =>
120
131
val arg = gen.unboxIfValueClass(field, args.head)
121
132
if field.owner.is(Trait ) then
122
133
gen.callMethod(tree)(qualifier, field.setter.asTerm, List (arg))
123
134
else gen.setField(tree)(qualifier, field, arg)
135
+
124
136
case ReflectEvalStrategy .MethodCall (method) => gen.callMethod(tree)(qualifier, method, args)
125
- case ReflectEvalStrategy .ConstructorCall (ctr , cls) => gen.callConstructor(tree)(qualifier, ctr , args)
137
+ case ReflectEvalStrategy .ConstructorCall (ctor , cls) => gen.callConstructor(tree)(qualifier, ctor , args)
126
138
case _ => super .transform(tree)
127
139
128
140
private def isReflectEval (symbol : Symbol )(using Context ): Boolean =
129
- symbol.name == termName( " reflectEval " ) && symbol.owner == config.expressionClass
141
+ symbol.name == reflectEvalName && symbol.owner == config.expressionClass
130
142
131
143
class Gen (reflectEval : Apply )(using Context ):
132
144
private val expressionThis = reflectEval.fun.asInstanceOf [Select ].qualifier
@@ -135,7 +147,7 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
135
147
val typeSymbol = term.info.typeSymbol.asType
136
148
JavaEncoding .encode(typeSymbol) match
137
149
case s " scala.runtime. ${_}Ref " =>
138
- val elemField = typeSymbol.info.decl(termName( " elem " ) ).symbol
150
+ val elemField = typeSymbol.info.decl(elemName ).symbol
139
151
getField(tree)(tree, elemField.asTerm)
140
152
case _ => tree
141
153
@@ -166,7 +178,7 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
166
178
callMethod(tree)(tree, unboxMethod, Nil )
167
179
168
180
def getThisObject : Tree =
169
- Apply (Select (expressionThis, termName(" getThisObject" )), List .empty )
181
+ Apply (Select (expressionThis, termName(" getThisObject" )), Nil )
170
182
171
183
def getLocalValue (name : String ): Tree =
172
184
Apply (
@@ -284,27 +296,27 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
284
296
case _ => result
285
297
end callMethod
286
298
287
- def callConstructor (tree : Tree )(qualifier : Tree , ctr : TermSymbol , args : List [Tree ]): Tree =
288
- val methodType = ctr .info.asInstanceOf [MethodType ]
299
+ def callConstructor (tree : Tree )(qualifier : Tree , ctor : TermSymbol , args : List [Tree ]): Tree =
300
+ val methodType = ctor .info.asInstanceOf [MethodType ]
289
301
val paramTypesNames = methodType.paramInfos.map(JavaEncoding .encode)
290
302
val clsName = JavaEncoding .encode(methodType.resType)
291
303
292
304
val capturedArgs =
293
305
methodType.paramNames.dropRight(args.size).map {
294
- case outer if outer.toString == " $outer " => qualifier
306
+ case outer if outer == nme. OUTER => qualifier
295
307
case name @ DerivedName (underlying, _) =>
296
308
// if derived then probably a capture
297
- capturedValue(tree : Tree )(ctr .owner, underlying)
309
+ capturedValue(tree : Tree )(ctor .owner, underlying)
298
310
.getOrElse {
299
- report.error(s " Unknown captured variable $name in $ctr of ${ctr .owner}" , reflectEval.srcPos)
311
+ report.error(s " Unknown captured variable $name in $ctor of ${ctor .owner}" , reflectEval.srcPos)
300
312
ref(defn.Predef_undefined )
301
313
}
302
314
case name =>
303
315
val paramName = JavaEncoding .encode(name)
304
316
getLocalValue(paramName)
305
317
}
306
318
307
- val erasedCtrInfo = atPhase(Phases .elimErasedValueTypePhase)(ctr .info)
319
+ val erasedCtrInfo = atPhase(Phases .elimErasedValueTypePhase)(ctor .info)
308
320
.asInstanceOf [MethodType ]
309
321
val unboxedArgs = erasedCtrInfo.paramInfos.takeRight(args.size).zip(args).map {
310
322
case (tpe : ErasedValueType , arg) => unboxValueClass(arg, tpe)
@@ -343,4 +355,4 @@ private class ResolveReflectEval(config: ExpressionCompilerConfig, expressionSto
343
355
getClassCapture(tree : Tree )(qualifier, originalName, cls)
344
356
345
357
private object ResolveReflectEval :
346
- val name = " resolve-reflect-eval "
358
+ val name = " resolvReflectEval "
0 commit comments