summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMartin Odersky <odersky@gmail.com>2009-04-07 15:56:59 +0000
committerMartin Odersky <odersky@gmail.com>2009-04-07 15:56:59 +0000
commit84bb943a9d4297c65cb6ba6f3a2dda33987f46ea (patch)
tree25714f27a9318cfdfdb85c829f3cfb436305363c /src
parentb17f6f68da05876ebb4172d3c54cb7680bd6f9e7 (diff)
downloadscala-84bb943a9d4297c65cb6ba6f3a2dda33987f46ea.tar.gz
scala-84bb943a9d4297c65cb6ba6f3a2dda33987f46ea.tar.bz2
scala-84bb943a9d4297c65cb6ba6f3a2dda33987f46ea.zip
fixed #1775 by making all anonymous functions s...
fixed #1775 by making all anonymous functions serializable. Small cleanups elsewhere.
Diffstat (limited to 'src')
-rwxr-xr-xsrc/compiler/scala/tools/nsc/javac/JavaParsers.scala11
-rw-r--r--src/compiler/scala/tools/nsc/symtab/Names.scala7
-rw-r--r--src/compiler/scala/tools/nsc/symtab/Symbols.scala20
-rw-r--r--src/compiler/scala/tools/nsc/symtab/Types.scala2
-rw-r--r--src/compiler/scala/tools/nsc/transform/CleanUp.scala4
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala6
6 files changed, 25 insertions, 25 deletions
diff --git a/src/compiler/scala/tools/nsc/javac/JavaParsers.scala b/src/compiler/scala/tools/nsc/javac/JavaParsers.scala
index da6726d743..688aff8fd9 100755
--- a/src/compiler/scala/tools/nsc/javac/JavaParsers.scala
+++ b/src/compiler/scala/tools/nsc/javac/JavaParsers.scala
@@ -387,29 +387,24 @@ trait JavaParsers extends JavaScanners {
def modifiers(inInterface: Boolean): Modifiers = {
var flags: Long = Flags.JAVA
// assumed true unless we see public/private/protected - see bug #1240
- var defaultAccess = true
var privateWithin: Name =
if (inInterface) nme.EMPTY.toTypeName else thisPackageName
while (true) {
- // if any explicit access modifier is present, we set privateWithin
- // to the empty package so the flag is correctly interpreted.
- if (List(PUBLIC, PROTECTED, PRIVATE) contains in.token) {
- defaultAccess = false
- privateWithin = nme.EMPTY.toTypeName
- }
-
in.token match {
case AT if (in.lookaheadToken != INTERFACE) =>
in.nextToken
annotation()
case PUBLIC =>
+ privateWithin = nme.EMPTY.toTypeName
in.nextToken
case PROTECTED =>
flags |= Flags.PROTECTED
+ //privateWithin = thisPackageName
in.nextToken
case PRIVATE =>
flags |= Flags.PRIVATE
+ privateWithin = nme.EMPTY.toTypeName
in.nextToken
case STATIC =>
flags |= Flags.STATIC
diff --git a/src/compiler/scala/tools/nsc/symtab/Names.scala b/src/compiler/scala/tools/nsc/symtab/Names.scala
index fbc67d51d0..c692f20761 100644
--- a/src/compiler/scala/tools/nsc/symtab/Names.scala
+++ b/src/compiler/scala/tools/nsc/symtab/Names.scala
@@ -348,6 +348,13 @@ class Names {
i > suffix.length
}
+ final def containsName(subname: Name): Boolean = {
+ var start = 0
+ val last = len - subname.length
+ while (start <= last && !startsWith(subname, start)) start += 1
+ start <= last
+ }
+
/** Return the subname with characters from start to end-1.
*
* @param from ...
diff --git a/src/compiler/scala/tools/nsc/symtab/Symbols.scala b/src/compiler/scala/tools/nsc/symtab/Symbols.scala
index 4e1710284b..021a3e1dbe 100644
--- a/src/compiler/scala/tools/nsc/symtab/Symbols.scala
+++ b/src/compiler/scala/tools/nsc/symtab/Symbols.scala
@@ -336,9 +336,9 @@ trait Symbols {
// class C extends D( { class E { ... } ... } ). Here, E is a class local to a constructor
final def isClassLocalToConstructor = isClass && hasFlag(INCONSTRUCTOR)
- final def isAnonymousClass = isClass && (originalName startsWith nme.ANON_CLASS_NAME)
- // startsWith necessary because name may grow when lifted and also because of anonymous function classes
- def isAnonymousFunction = hasFlag(SYNTHETIC) && (originalName startsWith nme.ANON_FUN_NAME)
+ final def isAnonymousClass = isClass && (originalName startsWith nme.ANON_CLASS_NAME) // todo: find out why we can't use containsName here.
+ final def isAnonymousFunction = hasFlag(SYNTHETIC) && (name containsName nme.ANON_FUN_NAME)
+
final def isRefinementClass = isClass && name == nme.REFINE_CLASS_NAME.toTypeName; // no lifting for refinement classes
final def isModuleClass = isClass && hasFlag(MODULE)
final def isPackageClass = isClass && hasFlag(PACKAGE)
@@ -378,6 +378,12 @@ trait Symbols {
originalName == nme.OUTER
}
+ /** Is this symbol an accessor method for outer? */
+ final def isOuterField = {
+ hasFlag(SYNTHETIC) &&
+ originalName == nme.OUTER_LOCAL
+ }
+
/** Does this symbol denote a stable value? */
final def isStable =
isTerm &&
@@ -532,14 +538,6 @@ trait Symbols {
else if (isContravariant) -1
else 0
- def isSerializable: Boolean = isMethod || {
- val typeSym = info.typeSymbol
- isValueType(typeSym) ||
- typeSym.hasAttribute(SerializableAttr) ||
- (info.baseClasses exists { bc => (bc hasAttribute SerializableAttr) || (bc == SerializableClass) }) ||
- (isClass && info.members.forall(_.isSerializable))
- }
-
// Flags, owner, and name attributes --------------------------------------------------------------
def owner: Symbol = rawowner
diff --git a/src/compiler/scala/tools/nsc/symtab/Types.scala b/src/compiler/scala/tools/nsc/symtab/Types.scala
index d61d56474c..dab101a15f 100644
--- a/src/compiler/scala/tools/nsc/symtab/Types.scala
+++ b/src/compiler/scala/tools/nsc/symtab/Types.scala
@@ -3774,7 +3774,7 @@ A type's typeSymbol should never be inspected directly.
}) || {
val tp1n = normalizePlus(tp1)
val tp2n = normalizePlus(tp2)
- ((tp1n ne tp1) || (tp2n ne tp2)) && isSubType0(tp1n, tp2n, depth)
+ ((tp1n ne tp1) || (tp2n ne tp2)) && isSubType(tp1n, tp2n, depth)
}
}
diff --git a/src/compiler/scala/tools/nsc/transform/CleanUp.scala b/src/compiler/scala/tools/nsc/transform/CleanUp.scala
index 23496807d8..bdf5bede41 100644
--- a/src/compiler/scala/tools/nsc/transform/CleanUp.scala
+++ b/src/compiler/scala/tools/nsc/transform/CleanUp.scala
@@ -758,9 +758,7 @@ abstract class CleanUp extends Transform {
if (settings.target.value == "jvm-1.4" || settings.target.value == "jvm-1.5") {
val sym = cdef.symbol
// is this an anonymous function class?
- if (sym.hasFlag(SYNTHETIC) && (sym.name.toString.indexOf("anonfun") != -1) &&
- !sym.hasAttribute(SerializableAttr) &&
- sym.isSerializable)
+ if (sym.isAnonymousFunction && !sym.hasAttribute(SerializableAttr))
sym.attributes =
AnnotationInfo(definitions.SerializableAttr.tpe, List(), List()) :: sym.attributes
}
diff --git a/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala b/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala
index 55e484e203..6e55404414 100644
--- a/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala
@@ -208,7 +208,7 @@ trait SyntheticMethods { self: Analyzer =>
localTyper.typed(methodDef)
}
- def isSerializable(clazz: Symbol): Boolean =
+ def hasSerializableAnnotation(clazz: Symbol): Boolean =
!clazz.getAttributes(definitions.SerializableAttr).isEmpty
def readResolveMethod: Tree = {
@@ -314,11 +314,13 @@ trait SyntheticMethods { self: Analyzer =>
ts += productElementMethod(accessors)
}
- if (clazz.isModuleClass && isSerializable(clazz)) {
+ if (clazz.isModuleClass && hasSerializableAnnotation(clazz)) {
// If you serialize a singleton and then deserialize it twice,
// you will have two instances of your singleton, unless you implement
// the readResolve() method (see http://www.javaworld.com/javaworld/
// jw-04-2003/jw-0425-designpatterns_p.html)
+ // question: should we do this for all serializable singletons, or (as currently done)
+ // only for those that carry a @serializable annotation?
if (!hasImplementation(nme.readResolve)) ts += readResolveMethod
}
if (!forCLDC && !forMSIL)