summaryrefslogtreecommitdiff
path: root/src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala
diff options
context:
space:
mode:
Diffstat (limited to 'src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala')
-rw-r--r--src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala46
1 files changed, 22 insertions, 24 deletions
diff --git a/src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala b/src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala
index b36d5d4ef1..d948d151a6 100644
--- a/src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala
+++ b/src/compiler/scala/tools/nsc/symtab/SymbolLoaders.scala
@@ -52,20 +52,28 @@ abstract class SymbolLoaders {
})
}
+ def newClass(owner: Symbol, name: String): ClassSymbol = owner.newClass(newTypeName(name))
+
/** Enter class with given `name` into scope of `root`
* and give them `completer` as type.
*/
- def enterClass(owner: Symbol, name: String, completer: SymbolLoader): Symbol = {
- val clazz = owner.newClass(newTypeName(name))
+ def enterClass(owner: Symbol, name: String, completer: SymbolLoader): Symbol =
+ enterClass(owner, newClass(owner, name), completer)
+
+ def enterClass(owner: Symbol, clazz: ClassSymbol, completer: SymbolLoader): Symbol = {
clazz setInfo completer
enterIfNew(owner, clazz, completer)
}
+ def newModule(owner: Symbol, name: String): ModuleSymbol = owner.newModule(newTermName(name))
+
/** Enter module with given `name` into scope of `root`
* and give them `completer` as type.
*/
- def enterModule(owner: Symbol, name: String, completer: SymbolLoader): Symbol = {
- val module = owner.newModule(newTermName(name))
+ def enterModule(owner: Symbol, name: String, completer: SymbolLoader): Symbol =
+ enterModule(owner, newModule(owner, name), completer)
+
+ def enterModule(owner: Symbol, module: ModuleSymbol, completer: SymbolLoader): Symbol = {
module setInfo completer
module.moduleClass setInfo moduleClassLoader
enterIfNew(owner, module, completer)
@@ -113,9 +121,12 @@ abstract class SymbolLoaders {
/** Enter class and module with given `name` into scope of `root`
* and give them `completer` as type.
*/
- def enterClassAndModule(root: Symbol, name: String, completer: SymbolLoader) {
- val clazz = enterClass(root, name, completer)
- val module = enterModule(root, name, completer)
+ def enterClassAndModule(root: Symbol, name: String, getCompleter: (ClassSymbol, ModuleSymbol) => SymbolLoader) {
+ val clazz = newClass(root, name)
+ val module = newModule(root, name)
+ val completer = getCompleter(clazz, module)
+ enterClass(root, clazz, completer)
+ enterModule(root, module, completer)
if (!clazz.isAnonymousClass) {
// Diagnostic for SI-7147
def msg: String = {
@@ -136,7 +147,7 @@ abstract class SymbolLoaders {
* (overridden in interactive.Global).
*/
def enterToplevelsFromSource(root: Symbol, name: String, src: AbstractFile) {
- enterClassAndModule(root, name, new SourcefileLoader(src))
+ enterClassAndModule(root, name, (_, _) => new SourcefileLoader(src))
}
/** The package objects of scala and scala.reflect should always
@@ -162,17 +173,10 @@ abstract class SymbolLoaders {
if (settings.verbose) inform("[symloader] no class, picked up source file for " + src.path)
enterToplevelsFromSource(owner, classRep.name, src)
case (Some(bin), _) =>
- enterClassAndModule(owner, classRep.name, newClassLoader(bin))
+ enterClassAndModule(owner, classRep.name, new ClassfileLoader(bin, _, _))
}
}
- /** Create a new loader from a binary classfile.
- * This is intended as a hook allowing to support loading symbols from
- * files other than .class files.
- */
- protected def newClassLoader(bin: AbstractFile): SymbolLoader =
- new ClassfileLoader(bin)
-
/**
* A lazy type that completes itself by calling parameter doComplete.
* Any linked modules/classes or module classes are also initialized.
@@ -277,7 +281,7 @@ abstract class SymbolLoaders {
}
}
- class ClassfileLoader(val classfile: AbstractFile) extends SymbolLoader with FlagAssigningCompleter {
+ class ClassfileLoader(val classfile: AbstractFile, clazz: ClassSymbol, module: ModuleSymbol) extends SymbolLoader with FlagAssigningCompleter {
private object classfileParser extends {
val symbolTable: SymbolLoaders.this.symbolTable.type = SymbolLoaders.this.symbolTable
} with ClassfileParser {
@@ -304,13 +308,7 @@ abstract class SymbolLoaders {
protected def doComplete(root: Symbol) {
val start = if (Statistics.canEnable) Statistics.startTimer(classReadNanos) else null
-
- // Running the classfile parser after refchecks can lead to "illegal class file dependency"
- // errors. More concretely, the classfile parser calls "sym.companionModule", which calls
- // "isModuleNotMethod" on the companion. After refchecks, this method forces the info, which
- // may run the classfile parser. This produces the error.
- enteringPhase(phaseBeforeRefchecks)(classfileParser.parse(classfile, root))
-
+ classfileParser.parse(classfile, clazz, module)
if (root.associatedFile eq NoAbstractFile) {
root match {
// In fact, the ModuleSymbol forwards its setter to the module class