@@ -18,6 +18,7 @@ import org.scalajs.ir
18
18
import ir .Position
19
19
import ir .Position .NoPosition
20
20
21
+ import org .scalajs .linker .backend .emitter .Emitter
21
22
import org .scalajs .linker .backend .javascript .Trees ._
22
23
import org .scalajs .linker .backend .javascript .SourceFileUtil
23
24
@@ -30,30 +31,65 @@ import java.lang.{Double => JDouble}
30
31
import java .net .URI
31
32
32
33
private [closure] object ClosureAstTransformer {
33
- def transformScript ( topLevelTrees : List [ Tree ], featureSet : FeatureSet ,
34
- relativizeBaseURI : Option [ URI ]) : Node = {
35
- val transformer = new ClosureAstTransformer (featureSet, relativizeBaseURI)
36
- transformer.transformScript(topLevelTrees)
37
- }
34
+ val emptyChunk = new Chunk ( Nil )
35
+
36
+ final class Chunk private [ ClosureAstTransformer ] (
37
+ private [ ClosureAstTransformer ] val nodes : List [ Node ]
38
+ ) extends Transformed . Value
38
39
}
39
40
40
- private class ClosureAstTransformer (featureSet : FeatureSet ,
41
- relativizeBaseURI : Option [URI ]) {
41
+ private [closure] class ClosureAstTransformer (featureSet : FeatureSet ,
42
+ relativizeBaseURI : Option [URI ]) extends Emitter .PostTransformer [ClosureAstTransformer .Chunk ] {
43
+ import ClosureAstTransformer .Chunk
44
+
42
45
private val dummySourceName = new java.net.URI (" virtualfile:scala.js-ir" )
43
46
44
- def transformScript (topLevelTrees : List [Tree ]): Node = {
47
+ def transformScript (chunks : List [Chunk ]): Node = {
45
48
val script = setNodePosition(new Node (Token .SCRIPT ), NoPosition )
46
- transformBlockStats(topLevelTrees)(NoPosition ).foreach(script.addChildToBack(_))
49
+
50
+ for {
51
+ chunk <- chunks
52
+ node <- chunk.nodes
53
+ } {
54
+ script.addChildToBack(node)
55
+ }
56
+
47
57
script.putProp(Node .FEATURE_SET , featureSet)
48
58
script
49
59
}
50
60
51
- def transformStat (tree : Tree )(implicit parentPos : Position ): Node =
61
+ def empty : Chunk = ClosureAstTransformer .emptyChunk
62
+
63
+ def transform (trees : List [Tree ]): Chunk =
64
+ new Chunk (transformBlockStats(trees)(NoPosition ))
65
+
66
+ private def transformStat (tree : Tree )(implicit parentPos : Position ): Node =
52
67
innerTransformStat(tree, tree.pos orElse parentPos)
53
68
54
69
private def innerTransformStat (tree : Tree , pos_in : Position ): Node = {
55
70
implicit val pos = pos_in
56
71
72
+ def newFixedPropNode (token : Token , static : Boolean , name : Ident ,
73
+ function : Node ): Node = {
74
+ val node = Node .newString(token, name.name)
75
+ node.addChildToBack(function)
76
+ node.setStaticMember(static)
77
+ node
78
+ }
79
+
80
+ /* This method should take a `prop: Node.Prop` parameter to factor out
81
+ * the `node.putBooleanProp()` that we find the three cases below. However,
82
+ * that is not possible because `Node.Prop` is private in `Node`. Go figure
83
+ * why Java allows to export as `public` the aliases
84
+ * `Node.COMPUTED_PROP_METHOD` et al. with a type that is not public ...
85
+ */
86
+ def newComputedPropNode (static : Boolean , nameExpr : Tree ,
87
+ function : Node ): Node = {
88
+ val node = new Node (Token .COMPUTED_PROP , transformExpr(nameExpr), function)
89
+ node.setStaticMember(static)
90
+ node
91
+ }
92
+
57
93
wrapTransform(tree) {
58
94
case VarDef (ident, optRhs) =>
59
95
val node = transformName(ident)
@@ -172,51 +208,6 @@ private class ClosureAstTransformer(featureSet: FeatureSet,
172
208
case classDef : ClassDef =>
173
209
transformClassDef(classDef)
174
210
175
- case _ =>
176
- // We just assume it is an expression
177
- new Node (Token .EXPR_RESULT , transformExpr(tree))
178
- }
179
- }
180
-
181
- private def transformClassDef (classDef : ClassDef )(
182
- implicit pos : Position ): Node = {
183
- val ClassDef (className, parentClass, members) = classDef
184
-
185
- val membersBlock = new Node (Token .CLASS_MEMBERS )
186
- for (member <- members)
187
- membersBlock.addChildToBack(transformClassMember(member))
188
- new Node (
189
- Token .CLASS ,
190
- className.fold(new Node (Token .EMPTY ))(transformName(_)),
191
- parentClass.fold(new Node (Token .EMPTY ))(transformExpr(_)),
192
- membersBlock)
193
- }
194
-
195
- private def transformClassMember (member : Tree ): Node = {
196
- implicit val pos = member.pos
197
-
198
- def newFixedPropNode (token : Token , static : Boolean , name : Ident ,
<
10000
/td>199
- function : Node ): Node = {
200
- val node = Node .newString(token, name.name)
201
- node.addChildToBack(function)
202
- node.setStaticMember(static)
203
- node
204
- }
205
-
206
- /* This method should take a `prop: Node.Prop` parameter to factor out
207
- * the `node.putBooleanProp()` that we find the three cases below. However,
208
- * that is not possible because `Node.Prop` is private in `Node`. Go figure
209
- * why Java allows to export as `public` the aliases
210
- * `Node.COMPUTED_PROP_METHOD` et al. with a type that is not public ...
211
- */
212
- def newComputedPropNode (static : Boolean , nameExpr : Tree ,
213
- function : Node ): Node = {
214
- val node = new Node (Token .COMPUTED_PROP , transformExpr(nameExpr), function)
215
- node.setStaticMember(static)
216
- node
217
- }
218
-
219
- wrapTransform(member) {
220
211
case MethodDef (static, name, args, restParam, body) =>
221
212
val function = genFunction(" " , args, restParam, body)
222
213
name match {
@@ -280,12 +271,27 @@ private class ClosureAstTransformer(featureSet: FeatureSet,
280
271
}
281
272
282
273
case _ =>
283
- throw new AssertionError (
284
- s " Unexpected class member tree of class ${member.getClass.getName} " )
274
+ // We just assume it is an expression
275
+ new Node ( Token . EXPR_RESULT , transformExpr( tree) )
285
276
}
286
277
}
287
278
288
- def transformExpr (tree : Tree )(implicit parentPos : Position ): Node =
279
EED3
+ private def transformClassDef (classDef : ClassDef )(
280
+ implicit pos : Position ): Node = {
281
+ val ClassDef (className, parentClass, members) = classDef
282
+
283
+ val membersBlock = new Node (Token .CLASS_MEMBERS )
284
+ for (node <- transformBlockStats(members))
285
+ membersBlock.addChildToBack(node)
286
+
287
+ new Node (
288
+ Token .CLASS ,
289
+ className.fold(new Node (Token .EMPTY ))(transformName(_)),
290
+ parentClass.fold(new Node (Token .EMPTY ))(transformExpr(_)),
291
+ membersBlock)
292
+ }
293
+
294
+ private def transformExpr (tree : Tree )(implicit parentPos : Position ): Node =
289
295
innerTransformExpr(tree, tree.pos orElse parentPos)
290
296
291
297
private def innerTransformExpr (tree : Tree , pos_in : Position ): Node = {
@@ -406,15 +412,15 @@ private class ClosureAstTransformer(featureSet: FeatureSet,
406
412
new Node (Token .FUNCTION , nameNode, paramList, transformBlock(body))
407
413
}
408
414
409
- def transformName (ident : Ident )(implicit parentPos : Position ): Node =
415
+ private def transformName (ident : Ident )(implicit parentPos : Position ): Node =
410
416
setNodePosition(Node .newString(Token .NAME , ident.name),
411
417
ident.pos orElse parentPos)
412
418
413
- def transformLabel (ident : Ident )(implicit parentPos : Position ): Node =
419
+ private def transformLabel (ident : Ident )(implicit parentPos : Position ): Node =
414
420
setNodePosition(Node .newString(Token .LABEL_NAME , ident.name),
415
421
ident.pos orElse parentPos)
416
422
417
- def transformObjectLitField (name : PropertyName , value : Tree )(
423
+ private def transformObjectLitField (name : PropertyName , value : Tree )(
418
424
implicit parentPos : Position ): Node = {
419
425
420
426
val transformedValue = transformExpr(value)
@@ -436,7 +442,7 @@ private class ClosureAstTransformer(featureSet: FeatureSet,
436
442
setNodePosition(node, name.pos.orElse(parentPos))
437
443
}
438
444
439
- def transformBlock (tree : Tree )(implicit parentPos : Position ): Node = {
445
+ private def transformBlock (tree : Tree )(implicit parentPos : Position ): Node = {
440
446
val pos = if (tree.pos.isDefined) tree.pos else parentPos
441
447
wrapTransform(tree) {
442
448
case Block (stats) =>
@@ -446,14 +452,14 @@ private class ClosureAstTransformer(featureSet: FeatureSet,
446
452
} (pos)
447
453
}
448
454
449
- def transformBlock (stats : List [Tree ], blockPos : Position ): Node = {
455
+ private def transformBlock (stats : List [Tree ], blockPos : Position ): Node = {
450
456
val block = new Node (Token .BLOCK )
451
457
for (node <- transformBlockStats(stats)(blockPos))
452
458
block.addChildToBack(node)
453
459
block
454
460
}
455
461
456
- def transformBlockStats (stats : List [Tree ])(
462
+ private def transformBlockStats (stats : List [Tree ])(
457
463
implicit parentPos : Position ): List [Node ] = {
458
464
459
465
@ inline def ctorDoc (): JSDocInfo = {
@@ -469,6 +475,10 @@ private class ClosureAstTransformer(featureSet: FeatureSet,
469
475
case DocComment (text) :: tss =>
470
476
loop(tss, nextIsCtor = text.startsWith(" @constructor" ), acc)
471
477
478
+ case Transformed (chunk : Chunk ) :: tss =>
479
+ assert(! nextIsCtor)
480
+ loop(tss, nextIsCtor = false , chunk.nodes reverse_:: : acc)
481
+
472
482
case t :: tss =>
473
483
val node = transformStat(t)
474
484
if (nextIsCtor) {
0 commit comments