diff --git a/compiler/frontend/src/org/jetbrains/kotlin/types/expressions/BasicExpressionTypingVisitor.java b/compiler/frontend/src/org/jetbrains/kotlin/types/expressions/BasicExpressionTypingVisitor.java index cb93326d188..b6bd1e73682 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/types/expressions/BasicExpressionTypingVisitor.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/types/expressions/BasicExpressionTypingVisitor.java @@ -178,8 +178,11 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor { @Override public KotlinTypeInfo visitConstantExpression(@NotNull KtConstantExpression expression, ExpressionTypingContext context) { - if (expression.getNode().getElementType() == KtNodeTypes.CHARACTER_CONSTANT) { - checkStringPrefixAndSuffix(expression, context); + IElementType elementType = expression.getNode().getElementType(); + if (elementType == KtNodeTypes.CHARACTER_CONSTANT + || elementType == KtNodeTypes.INTEGER_CONSTANT + || elementType == KtNodeTypes.FLOAT_CONSTANT) { + checkLiteralPrefixAndSuffix(expression, context); } CompileTimeConstant compileTimeConstant = components.constantExpressionEvaluator.evaluateExpression( @@ -192,7 +195,6 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor { compileTimeConstant != null ? ((TypedCompileTimeConstant) compileTimeConstant).getConstantValue() : null; boolean hasError = constantChecker.checkConstantExpressionType(constantValue, expression, context.expectedType); if (hasError) { - IElementType elementType = expression.getNode().getElementType(); return TypeInfoFactoryKt.createTypeInfo(getDefaultType(elementType), context); } } @@ -1482,7 +1484,7 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor { final ExpressionTypingContext context = contextWithExpectedType.replaceExpectedType(NO_EXPECTED_TYPE) .replaceContextDependency(INDEPENDENT); - checkStringPrefixAndSuffix(expression, context); + checkLiteralPrefixAndSuffix(expression, context); class StringTemplateVisitor extends KtVisitorVoid { private KotlinTypeInfo typeInfo = TypeInfoFactoryKt.noTypeInfo(context); @@ -1515,18 +1517,18 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor { contextWithExpectedType); } - private static void checkStringPrefixAndSuffix(@NotNull PsiElement expression, ExpressionTypingContext context) { - checkStringPrefixOrSuffix(PsiTreeUtil.prevLeaf(expression), context); - checkStringPrefixOrSuffix(PsiTreeUtil.nextLeaf(expression), context); + private static void checkLiteralPrefixAndSuffix(@NotNull PsiElement expression, ExpressionTypingContext context) { + checkLiteralPrefixOrSuffix(PsiTreeUtil.prevLeaf(expression), context); + checkLiteralPrefixOrSuffix(PsiTreeUtil.nextLeaf(expression), context); } - private static void checkStringPrefixOrSuffix(PsiElement prefixOrSuffix, ExpressionTypingContext context) { - if (illegalStringPrefixOrSuffix(prefixOrSuffix)) { - context.trace.report(Errors.UNSUPPORTED.on(prefixOrSuffix, "string prefixes and suffixes")); + private static void checkLiteralPrefixOrSuffix(PsiElement prefixOrSuffix, ExpressionTypingContext context) { + if (illegalLiteralPrefixOrSuffix(prefixOrSuffix)) { + context.trace.report(Errors.UNSUPPORTED.on(prefixOrSuffix, "literal prefixes and suffixes")); } } - private static boolean illegalStringPrefixOrSuffix(@Nullable PsiElement element) { + private static boolean illegalLiteralPrefixOrSuffix(@Nullable PsiElement element) { if (element == null) return false; IElementType elementType = element.getNode().getElementType(); diff --git a/compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.kt b/compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.kt new file mode 100644 index 00000000000..f927fd0cee0 --- /dev/null +++ b/compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.kt @@ -0,0 +1,54 @@ +// !DIAGNOSTICS: -UNUSED_PARAMETER -USELESS_CAST + +infix fun Any?.foo(a: Any) {} +infix fun Any?.zoo(a: Any) {} +infix fun Any?.Loo(a: Any) {} +infix fun Any?.doo(a: Any) {} +infix fun Any?.ddoo(a: Any) {} +operator fun Any?.contains(a: Any): Boolean = true + +fun test(a: Any) { + 1foo a + 1ffoo a + 1doo a + 1ddoo a + 1contains a + + 1Lfoo a + 1Loo a + 1LLoo a + + 0b1foo a + 0b1Lfoo a + 0b1Loo a + 0b1LLoo a + + 0xfoo a + 0xffoo a + 0xfLLoo a + + 1.0foo a + 1.0ffoo a + 1.0doo a + 1.0ddoo a + + .0foo a + .0ffoo a + .0doo a + .0ddoo a + + 1in a + 1.0in a + 1.0fin a + 1.0din a + .0in a + .0fin a + .0din a + + 1is Any + 1as Any + 1as? Any + + 1!is Any + 1!in a +} \ No newline at end of file diff --git a/compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.txt b/compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.txt new file mode 100644 index 00000000000..206db5b7547 --- /dev/null +++ b/compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.txt @@ -0,0 +1,9 @@ +package + +public fun test(/*0*/ a: kotlin.Any): kotlin.Unit +public infix fun kotlin.Any?.Loo(/*0*/ a: kotlin.Any): kotlin.Unit +public operator fun kotlin.Any?.contains(/*0*/ a: kotlin.Any): kotlin.Boolean +public infix fun kotlin.Any?.ddoo(/*0*/ a: kotlin.Any): kotlin.Unit +public infix fun kotlin.Any?.doo(/*0*/ a: kotlin.Any): kotlin.Unit +public infix fun kotlin.Any?.foo(/*0*/ a: kotlin.Any): kotlin.Unit +public infix fun kotlin.Any?.zoo(/*0*/ a: kotlin.Any): kotlin.Unit diff --git a/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestGenerated.java index 07dfcaabfba..29df31a2663 100644 --- a/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestGenerated.java @@ -403,6 +403,12 @@ public class DiagnosticsTestGenerated extends AbstractDiagnosticsTest { doTest(fileName); } + @TestMetadata("NumberPrefixAndSuffix.kt") + public void testNumberPrefixAndSuffix() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/NumberPrefixAndSuffix.kt"); + doTest(fileName); + } + @TestMetadata("ObjectWithConstructor.kt") public void testObjectWithConstructor() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/ObjectWithConstructor.kt");