diff options
author | Dmitry Petrashko <dmitry.petrashko@gmail.com> | 2016-08-09 13:31:33 +0200 |
---|---|---|
committer | Dmitry Petrashko <dmitry.petrashko@gmail.com> | 2016-08-09 13:31:33 +0200 |
commit | 594e8dd17b1b3c7f26a7ee979ecdf43d77a51cb1 (patch) | |
tree | 8f34a5f1e9f0ce761af86821d9a6433a932d4fe5 /src/dotty/tools/dotc/transform | |
parent | 62348dea92476f1bbb9d7f163f168be9c7e189b5 (diff) | |
download | dotty-594e8dd17b1b3c7f26a7ee979ecdf43d77a51cb1.tar.gz dotty-594e8dd17b1b3c7f26a7ee979ecdf43d77a51cb1.tar.bz2 dotty-594e8dd17b1b3c7f26a7ee979ecdf43d77a51cb1.zip |
Fix #1442: add new phase, SelectStatic
GenBCode has an implicit assumption that I wasn't aware of:
GetStatic should not be emitted against a valid selector.
If it is, GenBCode messes up the stack by not pop-ing the selector.
Surprisingly, this transformation is perfumed in nsc by flatten.
Diffstat (limited to 'src/dotty/tools/dotc/transform')
-rw-r--r-- | src/dotty/tools/dotc/transform/SelectStatic.scala | 37 |
1 files changed, 37 insertions, 0 deletions
diff --git a/src/dotty/tools/dotc/transform/SelectStatic.scala b/src/dotty/tools/dotc/transform/SelectStatic.scala new file mode 100644 index 000000000..fc79b7cbe --- /dev/null +++ b/src/dotty/tools/dotc/transform/SelectStatic.scala @@ -0,0 +1,37 @@ +package dotty.tools.dotc +package transform + +import dotty.tools.dotc.ast.tpd +import dotty.tools.dotc.core.Contexts.Context +import dotty.tools.dotc.core.DenotTransformers.IdentityDenotTransformer +import dotty.tools.dotc.core.Flags._ +import dotty.tools.dotc.core.Symbols._ +import dotty.tools.dotc.core._ +import dotty.tools.dotc.transform.TreeTransforms._ + +/** Removes selects that would be compiled into GetStatic + * otherwise backend needs to be aware that some qualifiers need to be dropped. + * Similar transformation seems to be performed by flatten in nsc + * + * @author Dmytro Petrashko + */ +class SelectStatic extends MiniPhaseTransform with IdentityDenotTransformer { thisTransform => + import ast.tpd._ + + override def phaseName: String = "selectStatic" + private val isPackage = FlagConjunction(PackageCreationFlags.bits) + + override def transformSelect(tree: tpd.Select)(implicit ctx: Context, info: TransformerInfo): tpd.Tree = { + val sym = tree.symbol + if (!sym.is(isPackage) && !sym.owner.is(isPackage) && + ( + ((sym is Flags.Module) && sym.owner.isStaticOwner) || + (sym is Flags.JavaStatic) || + (sym.owner is Flags.ImplClass) || + sym.hasAnnotation(ctx.definitions.ScalaStaticAnnot) + ) + ) + Block(List(tree.qualifier), ref(sym)) + else tree + } +} |