diff options
author | mihaylov <mihaylov@epfl.ch> | 2003-12-17 15:37:43 +0000 |
---|---|---|
committer | mihaylov <mihaylov@epfl.ch> | 2003-12-17 15:37:43 +0000 |
commit | b1d1e0190872782663296f35cadd06eb2966afc9 (patch) | |
tree | d146f1baf069c576cd77f88d15498e0cea9e7b1d /sources | |
parent | 373f59053719c293c77f72058dca84206a09ac81 (diff) | |
download | scala-b1d1e0190872782663296f35cadd06eb2966afc9.tar.gz scala-b1d1e0190872782663296f35cadd06eb2966afc9.tar.bz2 scala-b1d1e0190872782663296f35cadd06eb2966afc9.zip |
- added arithmetic conversions for chars
- handle Switch nodes by translating them to a multitude of if-else-ifs
Diffstat (limited to 'sources')
-rw-r--r-- | sources/scalac/backend/msil/GenMSIL.java | 30 |
1 files changed, 29 insertions, 1 deletions
diff --git a/sources/scalac/backend/msil/GenMSIL.java b/sources/scalac/backend/msil/GenMSIL.java index 2cb1c212b7..9c3760be97 100644 --- a/sources/scalac/backend/msil/GenMSIL.java +++ b/sources/scalac/backend/msil/GenMSIL.java @@ -608,6 +608,33 @@ public final class GenMSIL { sym2label.put(sym, l); return gen(rhs, toType); + case Switch(Tree test, int[] tags, Tree[] bodies, Tree otherwise): + LocalBuilder testLoc = code.DeclareLocal(tc.INT); + Item loc = items.LocalItem(MSILType.I4, testLoc); + boolean tmpLastStatement = lastStatement; + lastStatement = false; + load(gen(test)); + store(loc); + lastStatement = tmpLastStatement; + Label exit = code.DefineLabel(); + Label nextCase = code.DefineLabel(); + assert tags.length == bodies.length; + for (int i = 0; i < tags.length; i++) { + load(loc); + loadLiteral(MSILType.I4, new Integer(tags[i])); + code.Emit(OpCodes.Bne_Un, nextCase); + load(gen(bodies[i])); + if (lastStatement) + code.Emit(OpCodes.Ret); + else + code.Emit(OpCodes.Br, exit); + code.MarkLabel(nextCase); + nextCase = code.DefineLabel(); + } + Item i = load(gen(otherwise)); + code.MarkLabel(exit); + return i; + default: throw new ApplicationError("Dunno what to do: " + tree.getClass()); } @@ -714,6 +741,7 @@ public final class GenMSIL { void emitConvert(MSILType toType) { switch (toType) { + case BOOL: code.Emit(OpCodes.Conv_I4); break; // TODO: is this correct/best? case I1: code.Emit(OpCodes.Conv_I1); break; case I2: code.Emit(OpCodes.Conv_I2); break; case I4: code.Emit(OpCodes.Conv_I4); break; @@ -1884,7 +1912,7 @@ class MSILType { public static final MSILType OBJECT = REF(Type.GetType("System.Object")); public static final MSILType STRING_REF = REF(Type.GetType("System.String")); public static final MSILType [] ARITHM_PRECISION = - new MSILType[] {I1, I2, I4, I8, R4, R8}; + new MSILType[] {I1, I2, CHAR, I4, I8, R4, R8}; public static MSILType fromKind(int kind) { switch (kind) { |