Skip to content

Commit a7fab6d

Browse files
authored
Merge pull request #1445 from dotty-staging/fix-#1442
Fix #1442: add new phase, SelectStatic
2 parents 3179b03 + 376fa06 commit a7fab6d

File tree

4 files changed

+86
-1
lines changed

4 files changed

+86
-1
lines changed

src/dotty/tools/dotc/Compiler.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,7 @@ class Compiler {
9191
new Flatten, // Lift all inner classes to package scope
9292
new RestoreScopes), // Repair scopes rendered invalid by moving definitions in prior phases of the group
9393
List(new ExpandPrivate, // Widen private definitions accessed from nested classes
94+
new SelectStatic, // get rid of selects that would be compiled into GetStatic
9495
new CollectEntryPoints, // Find classes with main methods
9596
new CollectSuperCalls, // Find classes that are called with super
9697
new MoveStatics, // Move static methods to companion classes
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
package dotty.tools.dotc
2+
package transform
3+
4+
import dotty.tools.dotc.ast.Trees._
5+
import dotty.tools.dotc.ast.tpd
6+
import dotty.tools.dotc.core.Contexts.Context
7+
import dotty.tools.dotc.core.DenotTransformers.IdentityDenotTransformer
8+
import dotty.tools.dotc.core.Flags._
9+
import dotty.tools.dotc.core.Symbols._
10+
import dotty.tools.dotc.core._
11+
import dotty.tools.dotc.transform.TreeTransforms._
12+
13+
/** Removes selects that would be compiled into GetStatic
14+
* otherwise backend needs to be aware that some qualifiers need to be dropped.
15+
* Similar transformation seems to be performed by flatten in nsc
16+
* @author Dmytro Petrashko
17+
*/
18+
class SelectStatic extends MiniPhaseTransform with IdentityDenotTransformer { thisTransform =>
19+
import ast.tpd._
20+
21+
override def phaseName: String = "selectStatic"
22+
private val isPackage = FlagConjunction(PackageCreationFlags.bits)
23+
24+
override def transformSelect(tree: tpd.Select)(implicit ctx: Context, info: TransformerInfo): tpd.Tree = {
25+
val sym = tree.symbol
26+
val r1 =
27+
if (!sym.is(isPackage) && !sym.maybeOwner.is(isPackage) &&
28+
(
29+
((sym is Flags.Module) && sym.maybeOwner.isStaticOwner) ||
30+
(sym is Flags.JavaStatic) ||
31+
(sym.maybeOwner is Flags.ImplClass) ||
32+
sym.hasAnnotation(ctx.definitions.ScalaStaticAnnot)
33+
)
34+
)
35+
if (!tree.qualifier.symbol.is(JavaModule) && !tree.qualifier.isType)
36+
Block(List(tree.qualifier), ref(sym))
37+
else tree
38+
else tree
39+
40+
normalize(r1)
41+
}
42+
43+
private def normalize(t: Tree)(implicit ctx: Context) = t match {
44+
case Select(Block(stats, qual), nm) =>
45+
Block(stats, cpy.Select(t)(qual, nm))
46+
case Apply(Block(stats, qual), nm) =>
47+
Block(stats, Apply(qual, nm))
48+
case TypeApply(Block(stats, qual), nm) =>
49+
Block(stats, TypeApply(qual, nm))
50+
case _ => t
51+
}
52+
53+
override def transformApply(tree: tpd.Apply)(implicit ctx: Context, info: TransformerInfo): tpd.Tree = {
54+
normalize(tree)
55+
}
56+
57+
override def transformTypeApply(tree: tpd.TypeApply)(implicit ctx: Context, info: TransformerInfo): tpd.Tree = {
58+
normalize(tree)
59+
}
60+
}

tests/pos/i1442.scala

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
object Test1442 {
2+
final def sumMinimized[B](num: Numeric[B]): Int = {
3+
var cse: scala.math.Numeric.type = null.asInstanceOf[scala.math.Numeric.type]
4+
({cse = scala.math.Numeric; num eq cse.IntIsIntegral} ||
5+
(num eq cse.DoubleAsIfIntegral))
6+
2
7+
}
8+
9+
final def sum[B](implicit num: Numeric[B]): B = {
10+
// arithmetic series formula can be used for regular addition
11+
var cse: scala.math.Numeric.type = null.asInstanceOf[scala.math.Numeric.type]
12+
if ({cse = scala.math.Numeric; num eq cse.IntIsIntegral}||
13+
(num eq cse.BigIntIsIntegral)||
14+
(num eq cse.ShortIsIntegral)||
15+
(num eq cse.ByteIsIntegral)||
16+
(num eq cse.CharIsIntegral)||
17+
(num eq cse.LongIsIntegral)||
18+
(num eq cse.FloatAsIfIntegral)||
19+
(num eq cse.BigDecimalIsFractional)||
20+
(num eq cse.DoubleAsIfIntegral)) {
21+
null.asInstanceOf[B]
22+
} else null.asInstanceOf[B]
23+
}
24+
}

tests/run/t4859.check

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1+
Outer
12
Inner
23
Inner.i
34
About to reference Inner.i
4-
Outer
55
Inner.i
66
About to reference O.N
77
About to reference O.N

0 commit comments

Comments
 (0)