More robust icode loading and fixed an issue when dead-code eliminating closures that have live static fields.
git-svn-id: http://lampsvn.epfl.ch/svn-repos/scala/scala/trunk@22824 5e8d7ff9-d8ef-0310-90f0-a4852d11357a
This commit is contained in:
parent
f3bf344919
commit
c626d9b351
|
@ -385,7 +385,7 @@ trait BasicBlocks {
|
|||
|
||||
/** Close the block */
|
||||
def close {
|
||||
assert(!closed)
|
||||
assert(!closed || ignore)
|
||||
assert(instructionList.length > 0, "Empty block.")
|
||||
closed = true
|
||||
setFlag(DIRTYSUCCS)
|
||||
|
|
|
@ -42,11 +42,18 @@ trait Repository {
|
|||
}
|
||||
|
||||
/** Load bytecode for given symbol. */
|
||||
private def load(sym: Symbol) {
|
||||
val (c1, c2) = icodeReader.readClass(sym)
|
||||
|
||||
assert(c1.symbol == sym || c2.symbol == sym)
|
||||
loaded += (c1.symbol -> c1)
|
||||
loaded += (c2.symbol -> c2)
|
||||
def load(sym: Symbol) {
|
||||
try {
|
||||
val (c1, c2) = icodeReader.readClass(sym)
|
||||
|
||||
assert(c1.symbol == sym || c2.symbol == sym, "c1.symbol = %s, c2.symbol = %s, sym = %s".format(c1.symbol, c2.symbol, sym))
|
||||
loaded += (c1.symbol -> c1)
|
||||
loaded += (c2.symbol -> c2)
|
||||
} catch {
|
||||
case e: MissingRequirementError =>
|
||||
log("Failed to load %s. [%s]".format(sym.fullName, e.getMessage))
|
||||
if (settings.debug.value)
|
||||
e.printStackTrace
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -48,7 +48,7 @@ abstract class ClosureElimination extends SubComponent {
|
|||
idx -= 1
|
||||
}
|
||||
if (!liveOut(x)) {
|
||||
println("removing dead store/load " + x)
|
||||
log("removing dead store/load " + x)
|
||||
Some(Nil)
|
||||
} else None
|
||||
} else
|
||||
|
|
|
@ -160,6 +160,15 @@ abstract class DeadCodeElimination extends SubComponent {
|
|||
if (inliner.isClosureClass(sym)) {
|
||||
liveClosures += sym
|
||||
}
|
||||
|
||||
// it may be better to move static initializers from closures to
|
||||
// the enclosing class, to allow the optimizer to remove more closures.
|
||||
// right now, the only static fields in closures are created when caching
|
||||
// 'symbol literals.
|
||||
case LOAD_FIELD(sym, true) if inliner.isClosureClass(sym.owner) =>
|
||||
log("added closure class for field " + sym)
|
||||
liveClosures += sym.owner
|
||||
|
||||
case LOAD_EXCEPTION() =>
|
||||
()
|
||||
|
||||
|
|
|
@ -142,7 +142,7 @@ abstract class Inliners extends SubComponent {
|
|||
}
|
||||
|
||||
if (shouldLoadImplFor(concreteMethod, receiver))
|
||||
icodes.icode(concreteMethod.enclClass, true)
|
||||
icodes.load(concreteMethod.enclClass)
|
||||
|
||||
def isAvailable = icodes available concreteMethod.enclClass
|
||||
def isCandidate = isClosureClass(receiver) || concreteMethod.isEffectivelyFinal || receiver.isFinal
|
||||
|
|
|
@ -82,6 +82,7 @@ abstract class ClassfileParser {
|
|||
println("Skipping class: " + root + ": " + root.getClass)
|
||||
}
|
||||
*/
|
||||
log("parsing " + file.name)
|
||||
this.in = new AbstractFileReader(file)
|
||||
if (root.isModule) {
|
||||
this.clazz = root.companionClass
|
||||
|
|
|
@ -51,7 +51,7 @@ abstract class ICodeReader extends ClassfileParser {
|
|||
|
||||
classPath.findSourceFile(name) match {
|
||||
case Some(classFile) => parse(classFile, sym)
|
||||
case _ => log("Could not find: " + cls)
|
||||
case _ => throw new MissingRequirementError("Could not find bytecode for " + cls)
|
||||
}
|
||||
|
||||
(staticCode, instanceCode)
|
||||
|
|
Loading…
Reference in New Issue