diff options
author | Paul Phillips <paulp@improving.org> | 2012-05-04 17:44:28 -0700 |
---|---|---|
committer | Paul Phillips <paulp@improving.org> | 2012-05-04 18:24:16 -0700 |
commit | 0fb12fa0620c5f9999e309a4de7831549b283c24 (patch) | |
tree | 94a01f56b6ea8ed2dd2fdba0a8f9105e67f9d290 /src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala | |
parent | ecbf89552666ebba974188ef3c98b5f4855d0cea (diff) | |
download | scala-0fb12fa0620c5f9999e309a4de7831549b283c24.tar.gz scala-0fb12fa0620c5f9999e309a4de7831549b283c24.tar.bz2 scala-0fb12fa0620c5f9999e309a4de7831549b283c24.zip |
Updated Symbol to record classfile origin.
This change should be transparent to anything using sourceFile,
unless it was drinking from the inheritance well too deeply. Rather
than squander the already allocated field for every ClassSymbol not
being compiled from source, I'm now populating it with the file
representing the class. This will make a broad range of things easier,
like debugging, issuing useful error messages, symbol invalidation,
signature verification, you name it.
def sourceFile - still returns only source code files
def binaryFile - returns only class files
def associatedFile - returns whatever is there, if anything
Performance: I may be mistaken, but I believe this is a zero-impact
change. No new fields are allocated; fields which were null now hold
a useful reference. The reference is to a file instance which was
already being allocated and already long-lived.
Compare error messages:
// Version 1
% scalac a.scala
error: type _$1 is defined twice
// Version 2
% scalac a.scala
error: type _$1 is defined twice
conflicting symbols both originated in file './foo/package.class'
Note: this may be due to a bug in the compiler involving wildcards in package objects
one error found
Bonus for people who read commit logs. Try this in the repl
after starting power mode.
ListClass.info.members groupBy (_.associatedFile) foreach {
case (k, vs) => println("%s\n %s\n".format(k, vs map (_.defString) mkString "\n "))
}
Diffstat (limited to 'src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala')
-rw-r--r-- | src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala | 24 |
1 files changed, 14 insertions, 10 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala b/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala index 2d1369b11d..6932030fc2 100644 --- a/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala +++ b/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala @@ -622,19 +622,23 @@ trait ContextErrors { setError(tree) } - // checkNoDoubleDefs... - // @PP: I hacked the filename in (context0.unit) to work around SI-4893. It would be - // much better if every symbol could offer some idea of where it came from, else - // the obviously untrue claim that something has been defined twice can only frustrate. - // There's no direct test because partest doesn't work, but to reproduce, separately - // compile the next two lines: - // package object foo { val x: Class[_] = null } - // package foo def DefDefinedTwiceError(sym0: Symbol, sym1: Symbol) = { + // Most of this hard work is associated with SI-4893. val isBug = sym0.isAbstractType && sym1.isAbstractType && (sym0.name startsWith "_$") - issueSymbolTypeError(sym0, sym1+" is defined twice in " + context0.unit - + ( if (isBug) "\n(this error is likely due to a bug in the scala compiler involving wildcards in package objects)" else "" ) + val addendums = List( + if (sym0.associatedFile eq sym1.associatedFile) + Some("conflicting symbols both originated in file '%s'".format(sym0.associatedFile.canonicalPath)) + else if ((sym0.associatedFile ne null) && (sym1.associatedFile ne null)) + Some("conflicting symbols originated in files '%s' and '%s'".format(sym0.associatedFile.canonicalPath, sym1.associatedFile.canonicalPath)) + else None , + if (isBug) Some("Note: this may be due to a bug in the compiler involving wildcards in package objects") else None ) + val addendum = addendums.flatten match { + case Nil => "" + case xs => xs.mkString("\n ", "\n ", "") + } + + issueSymbolTypeError(sym0, sym1+" is defined twice" + addendum) } // cyclic errors |