Small fixes after review: do not set is_pure=true for named constants refactoring

This commit is contained in:
Natalia Ukhorskaya
2013-12-04 17:54:14 +04:00
parent 155cbbfc02
commit 27e602133d
12 changed files with 66 additions and 41 deletions
@@ -181,9 +181,9 @@ public class ConstantExpressionEvaluator private (val trace: BindingTrace) : Jet
val argumentsEntrySet = resolvedCall.getValueArguments().entrySet() val argumentsEntrySet = resolvedCall.getValueArguments().entrySet()
if (argumentsEntrySet.isEmpty()) { if (argumentsEntrySet.isEmpty()) {
val result = evaluateUnaryAndCheck(argumentForReceiver, resultingDescriptorName.asString(), callExpression) val result = evaluateUnaryAndCheck(argumentForReceiver, resultingDescriptorName.asString(), callExpression)
val isArgumentPure = trace.get(BindingContext.IS_PURE_CONSTANT_EXPRESSION, argumentForReceiver.expression) val isArgumentPure = trace.get(BindingContext.IS_PURE_CONSTANT_EXPRESSION, argumentForReceiver.expression) ?: false
val isNumberConventionMethod = resultingDescriptorName in OperatorConventions.NUMBER_CONVERSIONS val isNumberConversionMethod = resultingDescriptorName in OperatorConventions.NUMBER_CONVERSIONS
return createCompileTimeConstant(result, fullExpression, expectedType, !isNumberConventionMethod && isArgumentPure ?: false) return createCompileTimeConstant(result, fullExpression, expectedType, !isNumberConversionMethod && isArgumentPure)
} }
else if (argumentsEntrySet.size() == 1) { else if (argumentsEntrySet.size() == 1) {
val (parameter, argument) = argumentsEntrySet.first() val (parameter, argument) = argumentsEntrySet.first()
@@ -300,13 +300,9 @@ public class ConstantExpressionEvaluator private (val trace: BindingTrace) : Jet
return evaluateCall(expression, calleeExpression, receiverExpression, expectedType) return evaluateCall(expression, calleeExpression, receiverExpression, expectedType)
} }
// Mynum.A // MyEnum.A, Integer.MAX_VALUE
if (selectorExpression != null) { if (selectorExpression != null) {
val compileTimeConstant = evaluate(selectorExpression, expectedType) return evaluate(selectorExpression, expectedType)
if (compileTimeConstant != null) {
trace.record(BindingContext.IS_PURE_CONSTANT_EXPRESSION, expression, true);
}
return compileTimeConstant
} }
return null return null
@@ -364,7 +360,6 @@ public class ConstantExpressionEvaluator private (val trace: BindingTrace) : Jet
return null return null
} }
private class OperationArgument(val value: Any, val ctcType: CompileTimeType<*>, val expression: JetExpression) private class OperationArgument(val value: Any, val ctcType: CompileTimeType<*>, val expression: JetExpression)
private fun createOperationArgumentForReceiver(resolvedCall: ResolvedCall<*>, expression: JetExpression): OperationArgument? { private fun createOperationArgumentForReceiver(resolvedCall: ResolvedCall<*>, expression: JetExpression): OperationArgument? {
@@ -374,17 +369,7 @@ public class ConstantExpressionEvaluator private (val trace: BindingTrace) : Jet
val receiverCompileTimeType = getCompileTimeType(receiverExpressionType) val receiverCompileTimeType = getCompileTimeType(receiverExpressionType)
if (receiverCompileTimeType == null) return null if (receiverCompileTimeType == null) return null
val receiverValue = evaluate(expression, receiverExpressionType)?.getValue() return createOperationArgument(expression, receiverExpressionType, receiverCompileTimeType)
if (receiverValue == null) return null
if (receiverValue is NumberValueTypeConstructor<*>) {
val newValue = receiverValue.getValueForNumberType(receiverExpressionType)
if (newValue != null) {
return OperationArgument(newValue, receiverCompileTimeType, expression)
}
}
return OperationArgument(receiverValue, receiverCompileTimeType, expression)
} }
private fun createOperationArgumentForFirstParameter(argument: ResolvedValueArgument, parameter: ValueParameterDescriptor): OperationArgument? { private fun createOperationArgumentForFirstParameter(argument: ResolvedValueArgument, parameter: ValueParameterDescriptor): OperationArgument? {
@@ -397,20 +382,21 @@ public class ConstantExpressionEvaluator private (val trace: BindingTrace) : Jet
val argumentExpression = arguments.first().getArgumentExpression() val argumentExpression = arguments.first().getArgumentExpression()
if (argumentExpression == null) return null if (argumentExpression == null) return null
val constant = evaluate(argumentExpression, parameter.getType()) return createOperationArgument(argumentExpression, parameter.getType(), argumentCompileTimeType)
if (constant == null) return null }
val argumentValue = constant.getValue() private fun createOperationArgument(expression: JetExpression, expressionType: JetType, compileTimeType: CompileTimeType<*>): OperationArgument? {
if (argumentValue == null) return null val evaluationResult = evaluate(expression, expressionType)?.getValue()
if (evaluationResult == null) return null
if (argumentValue is NumberValueTypeConstructor<*>) { if (evaluationResult is NumberValueTypeConstructor<*>) {
val newValue = argumentValue.getValueForNumberType(parameter.getType()) val evaluationResultWithNewType = evaluationResult.getValueForNumberType(expressionType)
if (newValue != null) { if (evaluationResultWithNewType != null) {
return OperationArgument(newValue, argumentCompileTimeType, argumentExpression) return OperationArgument(evaluationResultWithNewType, compileTimeType, expression)
} }
} }
return OperationArgument(argumentValue, argumentCompileTimeType, argumentExpression) return OperationArgument(evaluationResult, compileTimeType, expression)
} }
fun createCompileTimeConstant(value: Any?, expression: JetExpression, expectedType: JetType?, isPure: Boolean = true): CompileTimeConstant<*>? { fun createCompileTimeConstant(value: Any?, expression: JetExpression, expectedType: JetType?, isPure: Boolean = true): CompileTimeConstant<*>? {
@@ -5,7 +5,6 @@ Retention(RetentionPolicy.RUNTIME)
annotation class Ann( annotation class Ann(
val p1: Int, val p1: Int,
val p2: Byte, val p2: Byte,
val p3: Byte,
val p4: Int, val p4: Int,
val p5: Int val p5: Int
) )
@@ -13,7 +12,6 @@ annotation class Ann(
Ann( Ann(
p1 = java.lang.Byte.MAX_VALUE + 1, p1 = java.lang.Byte.MAX_VALUE + 1,
p2 = 1 + 1, p2 = 1 + 1,
p3 = java.lang.Byte.MAX_VALUE - 1,
p4 = 1 + 1, p4 = 1 + 1,
p5 = 1.toByte() + 1 p5 = 1.toByte() + 1
) class MyClass ) class MyClass
@@ -22,7 +20,6 @@ fun box(): String {
val annotation = javaClass<MyClass>().getAnnotation(javaClass<Ann>())!! val annotation = javaClass<MyClass>().getAnnotation(javaClass<Ann>())!!
if (annotation.p1 != 128) return "fail 1, expected = ${128}, actual = ${annotation.p1}" if (annotation.p1 != 128) return "fail 1, expected = ${128}, actual = ${annotation.p1}"
if (annotation.p2 != 2.toByte()) return "fail 2, expected = ${2}, actual = ${annotation.p2}" if (annotation.p2 != 2.toByte()) return "fail 2, expected = ${2}, actual = ${annotation.p2}"
if (annotation.p3 != 126.toByte()) return "fail 3, expected = ${126}, actual = ${annotation.p3}"
if (annotation.p4 != 2) return "fail 4, expected = ${2}, actual = ${annotation.p4}" if (annotation.p4 != 2) return "fail 4, expected = ${2}, actual = ${annotation.p4}"
if (annotation.p5 != 2) return "fail 5, expected = ${2}, actual = ${annotation.p5}" if (annotation.p5 != 2) return "fail 5, expected = ${2}, actual = ${annotation.p5}"
return "OK" return "OK"
@@ -5,7 +5,6 @@ Retention(RetentionPolicy.RUNTIME)
annotation class Ann( annotation class Ann(
val p1: Int, val p1: Int,
val p2: Int, val p2: Int,
val p3: Long,
val p4: Long, val p4: Long,
val p5: Int val p5: Int
) )
@@ -13,7 +12,6 @@ annotation class Ann(
Ann( Ann(
p1 = java.lang.Integer.MAX_VALUE + 1, p1 = java.lang.Integer.MAX_VALUE + 1,
p2 = 1 + 1, p2 = 1 + 1,
p3 = java.lang.Integer.MAX_VALUE + 1,
p4 = 1 + 1, p4 = 1 + 1,
p5 = 1.toInt() + 1.toInt() p5 = 1.toInt() + 1.toInt()
) class MyClass ) class MyClass
@@ -22,7 +20,6 @@ fun box(): String {
val annotation = javaClass<MyClass>().getAnnotation(javaClass<Ann>())!! val annotation = javaClass<MyClass>().getAnnotation(javaClass<Ann>())!!
if (annotation.p1 != -2147483648) return "fail 1, expected = ${-2147483648}, actual = ${annotation.p1}" if (annotation.p1 != -2147483648) return "fail 1, expected = ${-2147483648}, actual = ${annotation.p1}"
if (annotation.p2 != 2) return "fail 2, expected = ${2}, actual = ${annotation.p2}" if (annotation.p2 != 2) return "fail 2, expected = ${2}, actual = ${annotation.p2}"
if (annotation.p3 != -2147483648.toLong()) return "fail 3, expected = ${-2147483648}, actual = ${annotation.p3}"
if (annotation.p4 != 2.toLong()) return "fail 4, expected = ${2}, actual = ${annotation.p4}" if (annotation.p4 != 2.toLong()) return "fail 4, expected = ${2}, actual = ${annotation.p4}"
if (annotation.p5 != 2) return "fail 5, expected = ${2}, actual = ${annotation.p5}" if (annotation.p5 != 2) return "fail 5, expected = ${2}, actual = ${annotation.p5}"
return "OK" return "OK"
@@ -0,0 +1,26 @@
fun fooInt(p: Int) = p
fun fooLong(p: Long) = p
fun fooByte(p: Byte) = p
fun fooShort(p: Short) = p
fun test() {
fooInt(1 plus 1)
fooByte(1 plus 1)
fooLong(1 plus 1)
fooShort(1 plus 1)
fooInt(1 times 1)
fooByte(1 times 1)
fooLong(1 times 1)
fooShort(1 times 1)
fooInt(1 div 1)
fooByte(1 div 1)
fooLong(1 div 1)
fooShort(1 div 1)
fooInt(1 mod 1)
fooByte(1 mod 1)
fooLong(1 mod 1)
fooShort(1 mod 1)
}
+1 -1
View File
@@ -2,7 +2,7 @@ package test
enum class MyEnum { A } enum class MyEnum { A }
// val prop1: true // val prop1: null
val prop1 = MyEnum.A val prop1 = MyEnum.A
// val prop2: null // val prop2: null
@@ -0,0 +1,9 @@
package test
val NAMED_CONSTANT = 1
// val prop1: null
val prop1 = NAMED_CONSTANT
// val prop2: null
val prop2 = NAMED_CONSTANT + 1
@@ -8,4 +8,4 @@ annotation class Ann(
Ann(1 + 1, java.lang.Long.MAX_VALUE + 1 - 1, java.lang.Long.MAX_VALUE - 1) class MyClass Ann(1 + 1, java.lang.Long.MAX_VALUE + 1 - 1, java.lang.Long.MAX_VALUE - 1) class MyClass
// EXPECTED: Ann[l1 = IntegerValueType(2): IntegerValueType(2), l2 = IntegerValueType(9223372036854775807): IntegerValueType(9223372036854775807), l3 = IntegerValueType(9223372036854775806): IntegerValueType(9223372036854775806)] // EXPECTED: Ann[l1 = IntegerValueType(2): IntegerValueType(2), l2 = 9223372036854775807.toLong(): jet.Long, l3 = 9223372036854775806.toLong(): jet.Long]
@@ -18,4 +18,4 @@ Ann(
p6 = java.lang.Long.MAX_VALUE + 1 p6 = java.lang.Long.MAX_VALUE + 1
) class MyClass ) class MyClass
// EXPECTED: Ann[p1 = IntegerValueType(128): IntegerValueType(128), p2 = IntegerValueType(32768): IntegerValueType(32768), p3 = IntegerValueType(-2147483648): IntegerValueType(-2147483648), p4 = IntegerValueType(-2147483648): IntegerValueType(-2147483648), p5 = 2147483648.toLong(): jet.Long, p6 = IntegerValueType(-9223372036854775808): IntegerValueType(-9223372036854775808)] // EXPECTED: Ann[p1 = 128.toInt(): jet.Int, p2 = 32768.toInt(): jet.Int, p3 = -2147483648.toInt(): jet.Int, p4 = -2147483648.toInt(): jet.Int, p5 = 2147483648.toLong(): jet.Long, p6 = -9223372036854775808.toLong(): jet.Long]
@@ -16,4 +16,4 @@ Ann(
p5 = 1.toByte() + 1.toByte() p5 = 1.toByte() + 1.toByte()
) class MyClass ) class MyClass
// EXPECTED: Ann[p1 = IntegerValueType(128): IntegerValueType(128), p2 = IntegerValueType(2): IntegerValueType(2), p3 = IntegerValueType(128): IntegerValueType(128), p4 = 2.toInt(): jet.Int, p5 = 2.toInt(): jet.Int] // EXPECTED: Ann[p1 = 128.toInt(): jet.Int, p2 = IntegerValueType(2): IntegerValueType(2), p3 = 128.toInt(): jet.Int, p4 = 2.toInt(): jet.Int, p5 = 2.toInt(): jet.Int]
@@ -16,4 +16,4 @@ Ann(
p5 = 1.toInt() + 1.toInt() p5 = 1.toInt() + 1.toInt()
) class MyClass ) class MyClass
// EXPECTED: Ann[p1 = IntegerValueType(-2147483648): IntegerValueType(-2147483648), p2 = IntegerValueType(2): IntegerValueType(2), p3 = IntegerValueType(-2147483648): IntegerValueType(-2147483648), p4 = 2.toInt(): jet.Int, p5 = 2.toInt(): jet.Int] // EXPECTED: Ann[p1 = -2147483648.toInt(): jet.Int, p2 = IntegerValueType(2): IntegerValueType(2), p3 = -2147483648.toInt(): jet.Int, p4 = 2.toInt(): jet.Int, p5 = 2.toInt(): jet.Int]
@@ -2779,6 +2779,11 @@ public class JetDiagnosticsTestGenerated extends AbstractDiagnosticsTestWithEage
doTest("compiler/testData/diagnostics/tests/evaluate/numberBinaryOperationsCall.kt"); doTest("compiler/testData/diagnostics/tests/evaluate/numberBinaryOperationsCall.kt");
} }
@TestMetadata("numberBinaryOperationsInfixCall.kt")
public void testNumberBinaryOperationsInfixCall() throws Exception {
doTest("compiler/testData/diagnostics/tests/evaluate/numberBinaryOperationsInfixCall.kt");
}
@TestMetadata("otherOverflow.kt") @TestMetadata("otherOverflow.kt")
public void testOtherOverflow() throws Exception { public void testOtherOverflow() throws Exception {
doTest("compiler/testData/diagnostics/tests/evaluate/otherOverflow.kt"); doTest("compiler/testData/diagnostics/tests/evaluate/otherOverflow.kt");
@@ -106,6 +106,11 @@ public class EvaluateExpressionTestGenerated extends AbstractEvaluateExpressionT
doIsPureTest("compiler/testData/evaluate/isPure/innerToType.kt"); doIsPureTest("compiler/testData/evaluate/isPure/innerToType.kt");
} }
@TestMetadata("namedConstants.kt")
public void testNamedConstants() throws Exception {
doIsPureTest("compiler/testData/evaluate/isPure/namedConstants.kt");
}
@TestMetadata("strings.kt") @TestMetadata("strings.kt")
public void testStrings() throws Exception { public void testStrings() throws Exception {
doIsPureTest("compiler/testData/evaluate/isPure/strings.kt"); doIsPureTest("compiler/testData/evaluate/isPure/strings.kt");