diff options
author | Iulian Dragos <jaguarul@gmail.com> | 2005-10-15 16:45:59 +0000 |
---|---|---|
committer | Iulian Dragos <jaguarul@gmail.com> | 2005-10-15 16:45:59 +0000 |
commit | d8522ed174ce5a098634b2b4a26d83a04a81554a (patch) | |
tree | b92eee6608d1cfa51674b4175fb8cd4b5ff095a4 /sources | |
parent | 11a9eecb4d8b406690b76230ff91e1fac01651a6 (diff) | |
download | scala-d8522ed174ce5a098634b2b4a26d83a04a81554a.tar.gz scala-d8522ed174ce5a098634b2b4a26d83a04a81554a.tar.bz2 scala-d8522ed174ce5a098634b2b4a26d83a04a81554a.zip |
Special treatment of scala.All and scala.AllRef...
Special treatment of scala.All and scala.AllRef in GenICode.
Diffstat (limited to 'sources')
-rw-r--r-- | sources/scala/tools/nsc/backend/icode/GenICode.scala | 43 | ||||
-rw-r--r-- | sources/scala/tools/nsc/backend/icode/Members.scala | 1 | ||||
-rw-r--r-- | sources/scala/tools/nsc/backend/jvm/GenJVM.scala | 47 |
3 files changed, 71 insertions, 20 deletions
diff --git a/sources/scala/tools/nsc/backend/icode/GenICode.scala b/sources/scala/tools/nsc/backend/icode/GenICode.scala index e170dfd5e7..1b84f0250c 100644 --- a/sources/scala/tools/nsc/backend/icode/GenICode.scala +++ b/sources/scala/tools/nsc/backend/icode/GenICode.scala @@ -40,8 +40,9 @@ abstract class GenICode extends SubComponent { // this depends on the backend! should be changed. val ANY_REF_CLASS = REFERENCE(definitions.ObjectClass); - val SCALA_ALL = REFERENCE(definitions.AllClass); - val THROWABLE = REFERENCE(definitions.ThrowableClass); + val SCALA_ALL = REFERENCE(definitions.AllClass); + val SCALA_ALLREF = REFERENCE(definitions.AllRefClass); + val THROWABLE = REFERENCE(definitions.ThrowableClass); /////////////////////////////////////////////////////////// @@ -96,15 +97,15 @@ abstract class GenICode extends SubComponent { log("Entering method " + name); val m = new IMethod(tree.symbol); m.sourceFile = unit.source.toString(); + m.returnType = if (tree.symbol.isConstructor) UNIT + else toTypeKind(tree.symbol.info.resultType); ctx.clazz.addMethod(m); var ctx1 = ctx.enterMethod(m, tree.asInstanceOf[DefDef]); addMethodParams(ctx1, vparamss); - val resTpe = if (tree.symbol.isConstructor) UNIT - else toTypeKind(ctx1.method.symbol.info.resultType); if (!m.isDeferred) { - ctx1 = genLoad(rhs, ctx1, resTpe); + ctx1 = genLoad(rhs, ctx1, m.returnType); // reverse the order of the local variables, to match the source-order m.locals = m.locals.reverse; @@ -112,7 +113,7 @@ abstract class GenICode extends SubComponent { rhs match { case Block(_, Return(_)) => (); case Return(_) => (); - case _ => ctx1.bb.emit(RETURN(resTpe), tree.pos); + case _ => ctx1.bb.emit(RETURN(m.returnType), rhs.pos); } ctx1.bb.close; } else @@ -222,8 +223,8 @@ abstract class GenICode extends SubComponent { ctx1 = genLoad(larg, ctx1, resKind); code match { case scalaPrimitives.POS => (); // nothing - case scalaPrimitives.NEG => ctx1.bb.emit(CALL_PRIMITIVE(Negation(resKind)), tree.pos); - case scalaPrimitives.NOT => ctx1.bb.emit(CALL_PRIMITIVE(Arithmetic(NOT, resKind)), tree.pos); + case scalaPrimitives.NEG => ctx1.bb.emit(CALL_PRIMITIVE(Negation(resKind)), larg.pos); + case scalaPrimitives.NOT => ctx1.bb.emit(CALL_PRIMITIVE(Arithmetic(NOT, resKind)), larg.pos); case _ => abort("Unknown unary operation: " + fun.symbol.fullNameString + " code: " + code); } generatedType = resKind; @@ -765,8 +766,17 @@ abstract class GenICode extends SubComponent { assert(generatedType != UNIT, "Can't convert from UNIT to " + expectedType); resCtx.bb.emit(CALL_PRIMITIVE(Conversion(generatedType, expectedType)), tree.pos); } - } else if (generatedType == SCALA_ALL && expectedType == UNIT) +// } else if (generatedType == SCALA_ALL && expectedType == UNIT) +// resCtx.bb.emit(DROP(generatedType)); + } else if (generatedType == SCALA_ALL) { resCtx.bb.emit(DROP(generatedType)); + resCtx.bb.emit(getZeroOf(ctx.method.returnType)); + resCtx.bb.emit(RETURN(ctx.method.returnType)); + resCtx.bb.enterIgnoreMode; + } else if (generatedType == SCALA_ALLREF) { + resCtx.bb.emit(DROP(generatedType)); + resCtx.bb.emit(CONSTANT(Constant(null))); + } resCtx; } @@ -858,6 +868,21 @@ abstract class GenICode extends SubComponent { case ARRAY(elem) => Literal(null: Any); } + def getZeroOf(k: TypeKind): Instruction = k match { + case UNIT => CONSTANT(Constant(())); + case BOOL => CONSTANT(Constant(false)); + case BYTE => CONSTANT(Constant(0: Byte)); + case SHORT => CONSTANT(Constant(0: Short)); + case CHAR => CONSTANT(Constant(0: Char)); + case INT => CONSTANT(Constant(0: Int)); + case LONG => CONSTANT(Constant(0: Long)); + case FLOAT => CONSTANT(Constant(0.0f)); + case DOUBLE => CONSTANT(Constant(0.0d)); + case REFERENCE(cls) => CONSTANT(Constant(null: Any)); + case ARRAY(elem) => CONSTANT(Constant(null: Any)); + } + + /** Is the given symbol a primitive operation? */ def isPrimitive(fun: Symbol): Boolean = { import scalaPrimitives._; diff --git a/sources/scala/tools/nsc/backend/icode/Members.scala b/sources/scala/tools/nsc/backend/icode/Members.scala index 14995a671d..c8f73ab368 100644 --- a/sources/scala/tools/nsc/backend/icode/Members.scala +++ b/sources/scala/tools/nsc/backend/icode/Members.scala @@ -157,6 +157,7 @@ trait Members: ICodes { var code: Code = null; var exh: List[ExceptionHandler] = _; var sourceFile: String = _; + var returnType: TypeKind = _; /** local variables and method parameters */ var locals: List[Local] = Nil; diff --git a/sources/scala/tools/nsc/backend/jvm/GenJVM.scala b/sources/scala/tools/nsc/backend/jvm/GenJVM.scala index 4b0621e6d0..971fff3eda 100644 --- a/sources/scala/tools/nsc/backend/jvm/GenJVM.scala +++ b/sources/scala/tools/nsc/backend/jvm/GenJVM.scala @@ -86,9 +86,6 @@ abstract class GenJVM extends SubComponent { ifaces, c.cunit.source.toString()); - clasz.fields foreach genField; - clasz.methods foreach genMethod; - if (isTopLevelModule(c.symbol)) { addModuleInstanceField; addStaticInit(jclass); @@ -99,6 +96,10 @@ abstract class GenJVM extends SubComponent { dumpMirrorClass; } + clasz.fields foreach genField; + clasz.methods foreach genMethod; + + addScalaAttribute(c.symbol); jclass.writeTo(getFile(jclass, ".class")); } @@ -106,6 +107,20 @@ abstract class GenJVM extends SubComponent { sym.isModuleClass && !sym.isImplClass && !sym.hasFlag(Flags.LIFTED) /* && !atPhase(currentRun.erasurePhase)(sym.isNestedClass) */ } + def addScalaAttribute(sym: Symbol): Unit = { + currentRun.symData.get(sym) match { + case Some(pickle) => + val scalaAttr = fjbgContext.JOtherAttribute(jclass, + jclass, + nme.ScalaSignatureATTR.toString(), + pickle.bytes, + pickle.writeIndex); + jclass.addAttribute(scalaAttr); + case _ => + log("Could not find pickle information for " + sym); + } + } + def genField(f: IField): Unit = { log("Adding field: " + f.symbol.fullNameString); jclass.addNewField(javaFlags(f.symbol), @@ -166,9 +181,6 @@ abstract class GenJVM extends SubComponent { clinit.emitINVOKESPECIAL(cls.getName(), JMethod.INSTANCE_CONSTRUCTOR_NAME, JMethodType.ARGLESS_VOID_FUNCTION); - clinit.emitPUTSTATIC(cls.getName(), - MODULE_INSTANCE_NAME, - jclass.getType()); clinit.emitRETURN(); } @@ -324,6 +336,16 @@ abstract class GenJVM extends SubComponent { jcode.emitINVOKESPECIAL(owner, javaName(method), javaType(method).asInstanceOf[JMethodType]); + + // we initialize the MODULE$ field immediately after the super ctor + if (isTopLevelModule(clasz.symbol) && + jmethod.getName() == JMethod.INSTANCE_CONSTRUCTOR_NAME && + javaName(method) == JMethod.INSTANCE_CONSTRUCTOR_NAME) { + jcode.emitALOAD_0(); + jcode.emitPUTSTATIC(jclass.getName(), + MODULE_INSTANCE_NAME, + jclass.getType()); + } } else jcode.emitINVOKESTATIC(owner, javaName(method), @@ -338,10 +360,6 @@ abstract class GenJVM extends SubComponent { case NEW(REFERENCE(cls)) => val className = javaName(cls); jcode.emitNEW(className); -// jcode.emitDUP(); -// jcode.emitINVOKESPECIAL(className, -// JMethod.INSTANCE_CONSTRUCTOR_NAME, -// javaType(ctor).asInstanceOf[JMethodType]); case CREATE_ARRAY(elem) => elem match { case REFERENCE(_) | ARRAY(_) => @@ -583,6 +601,10 @@ abstract class GenJVM extends SubComponent { case Conversion(src, dst) => log("Converting from: " + src + " to: " + dst); + if (dst == BOOL) { + + } + jcode.emitT2T(javaType(src), javaType(dst)); case ArrayLength(_) => @@ -671,6 +693,9 @@ abstract class GenJVM extends SubComponent { ////////////////////// Utilities //////////////////////// + /** Return the a name of this symbol that can be used on the Java + * platform. It removes spaces from names. + */ def javaName(sym: Symbol) = { val suffix = if (sym.hasFlag(Flags.MODULE) && !sym.isMethod && !sym.isImplClass && @@ -679,7 +704,7 @@ abstract class GenJVM extends SubComponent { (if (sym.isClass || (sym.isModule && !sym.isMethod)) sym.fullNameString('/') else - sym.simpleName.toString()) + suffix; + sym.simpleName.toString().trim()) + suffix; } def javaNames(syms: List[Symbol]): Array[String] = { |