提交 5b5e8119 编写于 作者: D Dmitry Jemerov

Float

上级 b6a078a5
......@@ -468,13 +468,14 @@ public class ExpressionCodegen extends JetVisitor {
}
DeclarationDescriptor op = bindingContext.resolveReferenceExpression(expression.getOperationReference());
if (op instanceof FunctionDescriptor) {
JetType returnType = bindingContext.getExpressionType(expression);
final Type asmType = typeMapper.mapType(returnType);
DeclarationDescriptor cls = op.getContainingDeclaration();
if (cls instanceof ClassDescriptor) {
final String className = cls.getName();
if (className.equals("Int") || className.equals("Long") || className.equals("Short") ||
className.equals("Byte") || className.equals("Char")) {
if (isNumberPrimitive(className)) {
if (op.getName().equals("compareTo")) {
generateCompareOp(expression, opToken);
generateCompareOp(expression, opToken, asmType);
}
else {
int opcode = opcodeForMethod(op.getName());
......@@ -486,10 +487,8 @@ public class ExpressionCodegen extends JetVisitor {
if (op.getName().equals("equals")) {
final Type leftType = typeMapper.mapType(bindingContext.getExpressionType(expression.getLeft()));
final Type rightType = typeMapper.mapType(bindingContext.getExpressionType(expression.getRight()));
if (isIntLikePrimitive(leftType) && isIntLikePrimitive(rightType)) {
gen(expression.getLeft(), Type.INT_TYPE);
gen(expression.getRight(), Type.INT_TYPE);
myStack.push(StackValue.icmp(opToken));
if (isNumberPrimitive(leftType) && leftType == rightType) {
generateCompareOp(expression, opToken, leftType);
return;
}
else {
......@@ -505,8 +504,14 @@ public class ExpressionCodegen extends JetVisitor {
throw new UnsupportedOperationException("Don't know how to generate binary op " + expression);
}
private static boolean isIntLikePrimitive(Type type) {
return type == Type.INT_TYPE || type == Type.SHORT_TYPE || type == Type.BYTE_TYPE || type == Type.CHAR_TYPE;
private static boolean isNumberPrimitive(String className) {
return className.equals("Int") || className.equals("Long") || className.equals("Short") ||
className.equals("Byte") || className.equals("Char") || className.equals("Float");
}
private static boolean isNumberPrimitive(Type type) {
return type == Type.INT_TYPE || type == Type.SHORT_TYPE || type == Type.BYTE_TYPE || type == Type.CHAR_TYPE ||
type == Type.FLOAT_TYPE;
}
private static int opcodeForMethod(final String name) {
......@@ -521,7 +526,7 @@ public class ExpressionCodegen extends JetVisitor {
private void generateBinaryOp(JetBinaryExpression expression, FunctionDescriptor op, int opcode) {
JetType returnType = op.getUnsubstitutedReturnType();
final Type asmType = typeMapper.mapType(returnType);
if (asmType == Type.INT_TYPE || asmType == Type.LONG_TYPE) {
if (asmType == Type.INT_TYPE || asmType == Type.LONG_TYPE || asmType == Type.FLOAT_TYPE) {
gen(expression.getLeft(), asmType);
gen(expression.getRight(), asmType);
v.visitInsn(asmType.getOpcode(opcode));
......@@ -532,10 +537,10 @@ public class ExpressionCodegen extends JetVisitor {
}
}
private void generateCompareOp(JetBinaryExpression expression, IElementType opToken) {
gen(expression.getLeft(), Type.INT_TYPE);
gen(expression.getRight(), Type.INT_TYPE);
myStack.push(StackValue.icmp(opToken));
private void generateCompareOp(JetBinaryExpression expression, IElementType opToken, Type type) {
gen(expression.getLeft(), type);
gen(expression.getRight(), type);
myStack.push(StackValue.cmp(opToken, type));
}
private void generateAssignmentExpression(JetBinaryExpression expression) {
......
......@@ -32,6 +32,9 @@ public class JetTypeMapper {
if (jetType.equals(standardLibrary.getCharType())) {
return Type.CHAR_TYPE;
}
if (jetType.equals(standardLibrary.getFloatType())) {
return Type.FLOAT_TYPE;
}
if (jetType.equals(standardLibrary.getBooleanType())) {
return Type.BOOLEAN_TYPE;
}
......
......@@ -27,8 +27,8 @@ public abstract class StackValue {
return new Constant(value);
}
public static StackValue icmp(IElementType opToken) {
return new IntCompare(opToken);
public static StackValue cmp(IElementType opToken, Type type) {
return new NumberCompare(opToken, type);
}
public abstract void condJump(Label label, boolean jumpIfFalse, InstructionAdapter v);
......@@ -113,11 +113,13 @@ public abstract class StackValue {
}
}
private static class IntCompare extends StackValue {
private static class NumberCompare extends StackValue {
private final IElementType opToken;
private final Type type;
public IntCompare(IElementType opToken) {
public NumberCompare(IElementType opToken, Type type) {
this.opToken = opToken;
this.type = type;
}
@Override
......@@ -136,26 +138,37 @@ public abstract class StackValue {
public void condJump(Label label, boolean jumpIfFalse, InstructionAdapter v) {
int opcode;
if (opToken == JetTokens.EQEQ) {
opcode = jumpIfFalse ? Opcodes.IF_ICMPNE : Opcodes.IF_ICMPEQ;
opcode = jumpIfFalse ? Opcodes.IFNE : Opcodes.IFEQ;
}
else if (opToken == JetTokens.EXCLEQ) {
opcode = jumpIfFalse ? Opcodes.IF_ICMPEQ : Opcodes.IF_ICMPNE;
opcode = jumpIfFalse ? Opcodes.IFEQ : Opcodes.IFNE;
}
else if (opToken == JetTokens.GT) {
opcode = jumpIfFalse ? Opcodes.IF_ICMPLE : Opcodes.IF_ICMPGT;
opcode = jumpIfFalse ? Opcodes.IFLE : Opcodes.IFGT;
}
else if (opToken == JetTokens.GTEQ) {
opcode = jumpIfFalse ? Opcodes.IF_ICMPLT : Opcodes.IF_ICMPGE;
opcode = jumpIfFalse ? Opcodes.IFLT : Opcodes.IFGE;
}
else if (opToken == JetTokens.LT) {
opcode = jumpIfFalse ? Opcodes.IF_ICMPGE : Opcodes.IF_ICMPLT;
opcode = jumpIfFalse ? Opcodes.IFGE : Opcodes.IFLT;
}
else if (opToken == JetTokens.LTEQ) {
opcode = jumpIfFalse ? Opcodes.IF_ICMPGT : Opcodes.IF_ICMPLE;
opcode = jumpIfFalse ? Opcodes.IFGT : Opcodes.IFLE;
}
else {
throw new UnsupportedOperationException("don't know how to generate this condjump");
}
if (type == Type.FLOAT_TYPE) {
if (opToken == JetTokens.GT || opToken == JetTokens.GTEQ) {
v.cmpg(type);
}
else {
v.cmpl(type);
}
}
else {
opcode += (Opcodes.IF_ICMPEQ - Opcodes.IFEQ);
}
v.visitJumpInsn(opcode, label);
}
}
......
......@@ -279,6 +279,14 @@ public class NamespaceGenTest extends LightCodeInsightFixtureTestCase {
binOpTest("fun foo(a: Char, b: Char): Int = a + b", 'A', (char) 3, (int) 'D');
}
public void testFloat() throws Exception {
binOpTest("fun foo(a: Float, b: Float): Float = a + b", 1.0f, 2.0f, 3.0f);
}
public void testFloatCmp() throws Exception {
binOpTest("fun foo(a: Float, b: Float): Boolean = a == b", 1.0f, 1.0f, true);
}
private void binOpTest(final String text, final Object arg1, final Object arg2, final Object expected) throws Exception {
loadText(text);
System.out.println(generateToText());
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册