summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorPaul Phillips <paulp@improving.org>2012-11-14 11:40:12 -0800
committerPaul Phillips <paulp@improving.org>2012-11-14 12:28:45 -0800
commit24958f7a8b1748be0c462b4563e652c9f7e24d6a (patch)
treeb5a0e79013273dbb359cc6fa46d59bfa38e7cc99 /src
parented6520b4fa002ea143cead5eb3633839d500e08d (diff)
downloadscala-24958f7a8b1748be0c462b4563e652c9f7e24d6a.tar.gz
scala-24958f7a8b1748be0c462b4563e652c9f7e24d6a.tar.bz2
scala-24958f7a8b1748be0c462b4563e652c9f7e24d6a.zip
Fix for SI-6664, cycle in case classes.
Scope lookup of an overloaded symbol was accidentally forcing some lazy info. Since as usual the caller didn't even have any interest in the symbol, but only in whether the name existed at all, I changed it call the method I made for this exact purpose, containsName. Also I much reduced the number of checks being made in the quest for an inherited copy method.
Diffstat (limited to 'src')
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/Namers.scala7
-rw-r--r--src/reflect/scala/reflect/internal/Scopes.scala8
2 files changed, 8 insertions, 7 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/Namers.scala b/src/compiler/scala/tools/nsc/typechecker/Namers.scala
index 3f5410eb45..04fb69671e 100644
--- a/src/compiler/scala/tools/nsc/typechecker/Namers.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/Namers.scala
@@ -909,11 +909,10 @@ trait Namers extends MethodSynthesis {
val modClass = companionSymbolOf(clazz, context).moduleClass
modClass.attachments.get[ClassForCaseCompanionAttachment] foreach { cma =>
val cdef = cma.caseClass
- def hasCopy(decls: Scope) = (decls lookup nme.copy) != NoSymbol
+ def hasCopy = (decls containsName nme.copy) || parents.exists(_ member nme.copy exists)
+
// SI-5956 needs (cdef.symbol == clazz): there can be multiple class symbols with the same name
- if (cdef.symbol == clazz && !hasCopy(decls) &&
- !parents.exists(p => hasCopy(p.typeSymbol.info.decls)) &&
- !parents.flatMap(_.baseClasses).distinct.exists(bc => hasCopy(bc.info.decls)))
+ if (cdef.symbol == clazz && !hasCopy)
addCopyMethod(cdef, templateNamer)
}
}
diff --git a/src/reflect/scala/reflect/internal/Scopes.scala b/src/reflect/scala/reflect/internal/Scopes.scala
index a593a412d7..950e30dbc5 100644
--- a/src/reflect/scala/reflect/internal/Scopes.scala
+++ b/src/reflect/scala/reflect/internal/Scopes.scala
@@ -242,7 +242,8 @@ trait Scopes extends api.Scopes { self: SymbolTable =>
// than a non-deterministic bizarre one (see any bug involving overloads
// in package objects.)
val alts = lookupAll(name).toList
- log("!!! scope lookup of $name found multiple symbols: $alts")
+ def alts_s = alts map (s => s.defString) mkString " <and> "
+ log(s"!!! scope lookup of $name found multiple symbols: $alts_s")
// FIXME - how is one supposed to create an overloaded symbol without
// knowing the correct owner? Using the symbol owner is not correct;
// say for instance this is List's scope and the symbols are its three
@@ -254,8 +255,9 @@ trait Scopes extends api.Scopes { self: SymbolTable =>
// FIXME - a similar question for prefix, although there are more
// clues from the symbols on that one, as implemented here. In general
// the distinct list is one type and lub becomes the identity.
- val prefix = lub(alts map (_.info.prefix) distinct)
- NoSymbol.newOverloaded(prefix, alts)
+ // val prefix = lub(alts map (_.info.prefix) distinct)
+ // Now using NoSymbol and NoPrefix always to avoid forcing info (SI-6664)
+ NoSymbol.newOverloaded(NoPrefix, alts)
}
}