summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorBurak Emir <emir@epfl.ch>2006-09-06 13:13:37 +0000
committerBurak Emir <emir@epfl.ch>2006-09-06 13:13:37 +0000
commit0482a0c416de901c9e3cb4f5efc3b6134358ee55 (patch)
tree09104c82b97cbf9043d428729619fb9d87f41179 /src
parent55f38ed459fdbbd2bd5d52b3807e663f9cf9b591 (diff)
downloadscala-0482a0c416de901c9e3cb4f5efc3b6134358ee55.tar.gz
scala-0482a0c416de901c9e3cb4f5efc3b6134358ee55.tar.bz2
scala-0482a0c416de901c9e3cb4f5efc3b6134358ee55.zip
prelim outer stuff
Diffstat (limited to 'src')
-rw-r--r--src/compiler/scala/tools/nsc/matching/PatternMatchers.scala117
-rw-r--r--src/compiler/scala/tools/nsc/transform/ExplicitOuter.scala34
2 files changed, 47 insertions, 104 deletions
diff --git a/src/compiler/scala/tools/nsc/matching/PatternMatchers.scala b/src/compiler/scala/tools/nsc/matching/PatternMatchers.scala
index dd8c16bbbf..7e5bfc10e8 100644
--- a/src/compiler/scala/tools/nsc/matching/PatternMatchers.scala
+++ b/src/compiler/scala/tools/nsc/matching/PatternMatchers.scala
@@ -1113,101 +1113,34 @@ trait PatternMatchers requires (transform.ExplicitOuter with PatternNodes) {
return toTree(node.and);
case ConstrPat(casted) =>
+ def outerAlwaysEqual(left: Type, right: Type) = Pair(left,right) match {
+ case Pair(TypeRef(lprefix, _,_), TypeRef(rprefix,_,_)) if lprefix =:= rprefix =>
+ true
+ case _ =>
+ false
+ }
var cond = gen.mkIsInstanceOf(selector.duplicate, node.getTpe())
- if(!settings.Xnofancymatch.value) {
- // compare outer instance for patterns like foo1.Bar foo2.Bar if not statically known to match
- casted.tpe match {
- case TypeRef(prefix,_,_) if (prefix.symbol.isTerm && !prefix.symbol.isPackage) =>
- selector.tpe match {
- case TypeRef(oprefix,_,_) =>
- if(oprefix =:= prefix)
- {} // statically known to match
- else {
-
- /* <-- start borrowed from explicitOuter */
-
- def outerClass(clazz: Symbol): Symbol =
- if (clazz.owner.isClass) clazz.owner
- else outerClass(if (clazz.isClassLocalToConstructor) clazz.owner.owner else clazz.owner)
-
- /** The first outer selection from currently transformed tree
- */
- def outerValue: Tree =
- outerSelect(gen.mkAttributedThis(owner.enclClass))
-
- /** The path
- * `base'.$outer ... .$outer
- * which refers to the outer instance 'to' of value 'base'
- */
- def outerPath(base: Tree, to: Symbol): Tree =
- if (base.tpe.symbol == to) base else outerPath(outerSelect(base), to)
-
- /** Select and apply outer accessor from 'base'
- */
- def outerSelect(base: Tree): Tree = {
- val otp = outerClass(base.tpe.symbol).thisType
- Apply(
- Select(base, outerMember(base.tpe)) setType MethodType(List(), otp),
- List()) setType otp
- }
+ // compare outer instance for patterns like foo1.Bar foo2.Bar if not statically known to match
+
+ if(!outerAlwaysEqual(casted.tpe, selector.tpe)) {
+ casted.tpe match {
+ case TypeRef(prefix,_,_) if (prefix.symbol.isTerm && !prefix.symbol.isPackage) =>
+ var theRef = gen.mkAttributedRef(prefix.prefix, prefix.symbol) // needs explicitouter treatment
+ if(global.settings.debug.value) {
+ Console.println("theRef "+theRef)
+ Console.println("handleOuter(theRef) "+handleOuter(theRef))
+ }
+ theRef = handleOuter(theRef)
- def outerMember(tp: Type): Symbol = {
- var e = tp.symbol.info.decls.elems
- // note: tp.decls does not work here, because tp might be a ThisType, in which case
- // its decls would be the decls of the required type of the class.
- while (e != null && !(e.sym.originalName.startsWith(nme.OUTER) && (e.sym hasFlag Flags.ACCESSOR)))
- e = e.next;
- assert(e != null, tp)
- e.sym
- }
- /* <-- end borrowed from explicitOuter */
-// Console.println(prefix)
-// Console.println(prefix.symbol)
-// Console.println(prefix.symbol.isModule)
-// Console.println("pre.pre "+prefix.prefix)
-// Console.println("pre.pre asSF "+prefix.prefix.asSeenFrom(owner.enclClass.tpe, owner.enclClass))
- var theRef = gen.mkAttributedRef(prefix.prefix, prefix.symbol) // problem: this needs explicitouter treatment
-
- // transform explicitOuter
- /** The first-step transformation method */
- def mytransform(tree: Tree): Tree = {
- val sym = tree.symbol
- tree match {
- case This(qual) =>
- if (sym == owner.enclClass || (sym hasFlag Flags.MODULE) && sym.isStatic) tree
- else posAssigner.atPos(tree.pos)(outerPath(outerValue, sym)); // (5)
- case Select(qual,name) =>
- Select(mytransform(qual),name)
- }
- }
- //theRef = mytransform(theRef)
- if(global.settings.debug.value) {
- Console.println("theRef "+theRef)
- Console.println("mytransform(theRef) "+mytransform(theRef))
- Console.println("handleOuter(theRef) "+handleOuter(theRef))
- }
- theRef = handleOuter(theRef)
- /*
- val tpe = prefix.prefix
- if(
- prefix.prefix match {
- case ThisType(q) =>
- Console.println("hello"+q)
- Console.println("but enclClass"+prefix.symbol.enclClass)
- case x => Console.println("hola"+x.getClass())
- }
- */
- cond = And(cond,
- Eq(Apply(Select(
- gen.mkAsInstanceOf(selector.duplicate, node.getTpe(), true), nme.OUTER),List()), theRef))
- }
- case _ =>
- //ignore
- }
- case _ =>
- //ignore
+ if(node.getTpe().decls.lookup(nme.OUTER) != NoSymbol) { // some guys don't have outers :-(
+ cond = And(cond,
+ Eq(Apply(Select(
+ gen.mkAsInstanceOf(selector.duplicate, node.getTpe(), true), nme.OUTER),List()), theRef))
+ }
+ case _ =>
+ //ignore ;
+ }
}
- }
return myIf(cond,
Block(
List(ValDef(casted,
diff --git a/src/compiler/scala/tools/nsc/transform/ExplicitOuter.scala b/src/compiler/scala/tools/nsc/transform/ExplicitOuter.scala
index 5811c279c8..762572b7af 100644
--- a/src/compiler/scala/tools/nsc/transform/ExplicitOuter.scala
+++ b/src/compiler/scala/tools/nsc/transform/ExplicitOuter.scala
@@ -337,10 +337,21 @@ with PatternMatchers {
*/
private val secondTransformer = new OuterPathTransformer {
+ def handleSelect(tree:Select) = tree match {
+ case Select(qual, name) =>
+ val sym = tree.symbol
+ val enclClass = currentOwner.enclClass
+ if (enclClass != sym.owner && enclClass != sym.moduleClass) // (3)
+ sym.makeNotPrivate(sym.owner);
+ val qsym = qual.tpe.widen.symbol
+ if ((sym hasFlag PROTECTED) && //(4)
+ (qsym.isTrait || !(qual.isInstanceOf[Super] || (qsym isSubClass enclClass))))
+ sym setFlag notPROTECTED;
+ }
+
/** The second-step transformation method */
override def transform(tree: Tree): Tree = {
val sym = tree.symbol
-
val tree1 =
if(tree.isInstanceOf[Match]) {
//Console.println("calling super.transform of Match with ncases "+
@@ -354,18 +365,11 @@ with PatternMatchers {
if (sym.owner.isTrait && (sym hasFlag (ACCESSOR | SUPERACCESSOR)))
sym.makeNotPrivate(sym.owner); //(2)
tree1
- case Select(qual, name) =>
- val enclClass = currentOwner.enclClass
- if (enclClass != sym.owner && enclClass != sym.moduleClass) // (3)
- sym.makeNotPrivate(sym.owner);
- val qsym = qual.tpe.widen.symbol
- if ((sym hasFlag PROTECTED) && //(4)
- (qsym.isTrait || !(qual.isInstanceOf[Super] || (qsym isSubClass enclClass))))
- sym setFlag notPROTECTED;
+ case tree @ Select(qual, name) =>
+ handleSelect(tree)
tree1
-/*<--- begin transmatch experimental */
- case Match(selector, cases) =>
+ case Match(selector, cases) => // <----- transmatch hook
val tid = cunit.fresh.newName("tidmark")
if(settings.debug.value)
@@ -385,7 +389,13 @@ with PatternMatchers {
if (sym == currentOwner.enclClass || (sym hasFlag Flags.MODULE) && sym.isStatic) tree
else atPos(tree.pos)(outerPath(outerValue, sym)); // (5)
case Select(qual,name) =>
- Select(mytransform(qual),name)
+ val s = copy.Select(tree, mytransform(qual), name)
+ handleSelect(s)
+ s
+ case x =>
+ if(settings.debug.value)
+ Console.println(x.getClass())
+ x
}
}
val t_untyped = ExplicitOuter.this.handlePattern(nselector, ncases.asInstanceOf[List[CaseDef]], currentOwner, mytransform)