diff options
author | Iulian Dragos <jaguarul@gmail.com> | 2007-06-27 14:26:47 +0000 |
---|---|---|
committer | Iulian Dragos <jaguarul@gmail.com> | 2007-06-27 14:26:47 +0000 |
commit | b4b91dcb58b5804f7ec1513e8f4d1e4534fd8018 (patch) | |
tree | 758a2817dd728101980c7ffc3f206d484ad77ba0 /src/compiler/scala/tools/nsc/typechecker/RefChecks.scala | |
parent | a1ec75c2642396a83854510ba7e88d8a302a67fd (diff) | |
download | scala-b4b91dcb58b5804f7ec1513e8f4d1e4534fd8018.tar.gz scala-b4b91dcb58b5804f7ec1513e8f4d1e4534fd8018.tar.bz2 scala-b4b91dcb58b5804f7ec1513e8f4d1e4534fd8018.zip |
Merged lazy values branch to trunk.
Diffstat (limited to 'src/compiler/scala/tools/nsc/typechecker/RefChecks.scala')
-rw-r--r-- | src/compiler/scala/tools/nsc/typechecker/RefChecks.scala | 29 |
1 files changed, 25 insertions, 4 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/RefChecks.scala b/src/compiler/scala/tools/nsc/typechecker/RefChecks.scala index bad97b2d1c..162d291ddd 100644 --- a/src/compiler/scala/tools/nsc/typechecker/RefChecks.scala +++ b/src/compiler/scala/tools/nsc/typechecker/RefChecks.scala @@ -566,6 +566,11 @@ abstract class RefChecks extends InfoTransform { stats1 } + /** Implements lazy value accessors: + * - for lazy fields inside traits, the rhs is the initializer itself + * - for all other lazy values z the accessor is a block of this form: + * { z = <rhs>; z } where z can be an identifier or a field. + */ def transformStat(tree: Tree, index: int): List[Tree] = tree match { case ModuleDef(mods, name, impl) => val sym = tree.symbol @@ -622,11 +627,27 @@ abstract class RefChecks extends InfoTransform { case ValDef(_, _, _, _) => val tree1 = transform(tree); // important to do before forward reference check - if (tree.symbol.isLocal && index <= currentLevel.maxindex) { - if (settings.debug.value) Console.println(currentLevel.refsym); - unit.error(currentLevel.refpos, "forward reference extends over definition of " + tree.symbol); + val ValDef(_, _, _, rhs) = tree1 + if (tree.symbol.hasFlag(LAZY)) { + assert(tree.symbol.isTerm, tree.symbol) + val vsym = tree.symbol + val lazyDefSym = vsym.lazyAccessor + assert(lazyDefSym != NoSymbol, vsym) + val lazyDef = atPos(tree.pos)( + DefDef(lazyDefSym, vparamss => + if (tree.symbol.owner.isTrait) rhs // for traits, this is further tranformed in mixins + else Block(List( + Assign(gen.mkAttributedRef(vsym), rhs)), + gen.mkAttributedRef(vsym)))) + log("Made lazy def: " + lazyDef) + typed(ValDef(vsym, EmptyTree)) :: typed(lazyDef) :: Nil + } else { + if (tree.symbol.isLocal && index <= currentLevel.maxindex && !tree.symbol.hasFlag(LAZY)) { + if (settings.debug.value) Console.println(currentLevel.refsym); + unit.error(currentLevel.refpos, "forward reference extends over definition of " + tree.symbol); + } + List(tree1) } - List(tree1) case Import(_, _) => List() |