Weaken PRIVATE_CLASS_MEMBER_FROM_INLINE diagnostic

This commit is contained in:
Michael Bogdanov
2016-02-11 17:41:03 +03:00
parent 384d2ea0d1
commit 4f0f81155a
7 changed files with 56 additions and 3 deletions
@@ -52,12 +52,13 @@ class InlineChecker implements CallChecker {
private final SimpleFunctionDescriptor descriptor;
private final Set<CallableDescriptor> inlinableParameters = new LinkedHashSet<CallableDescriptor>();
private final boolean isEffectivelyPublicApiFunction;
private final boolean isEffectivelyPrivateApiFunction;
public InlineChecker(@NotNull SimpleFunctionDescriptor descriptor) {
assert InlineUtil.isInline(descriptor) : "This extension should be created only for inline functions: " + descriptor;
this.descriptor = descriptor;
this.isEffectivelyPublicApiFunction = DescriptorUtilsKt.isEffectivelyPublicApi(descriptor);
this.isEffectivelyPrivateApiFunction = DescriptorUtilsKt.isEffectivelyPrivateApi(descriptor);
for (ValueParameterDescriptor param : descriptor.getValueParameters()) {
if (isInlinableParameter(param)) {
inlinableParameters.add(param);
@@ -253,7 +254,7 @@ class InlineChecker implements CallChecker {
@NotNull KtElement expression,
@NotNull BasicCallResolutionContext context
) {
if (!Visibilities.isPrivate(descriptor.getVisibility())) {
if (!isEffectivelyPrivateApiFunction) {
if (DescriptorUtilsKt.isInsidePrivateClass(declarationDescriptor)) {
context.trace.report(Errors.PRIVATE_CLASS_MEMBER_FROM_INLINE.on(expression, declarationDescriptor, descriptor));
}
@@ -0,0 +1,5 @@
import test.*
fun box() : String {
return Test().run()
}
@@ -0,0 +1,21 @@
package test
class Test {
private abstract class Base {
protected fun duplicate(s: String) = s + "K"
protected inline fun doInline(block: () -> String): String {
return duplicate(block())
}
}
private class Extender: Base() {
fun doSomething(): String {
return doInline { "O" }
}
}
fun run(): String {
return Extender().doSomething();
}
}
@@ -1381,6 +1381,12 @@ public class BlackBoxInlineCodegenTestGenerated extends AbstractBlackBoxInlineCo
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/codegen/boxInline/private"), Pattern.compile("^(.+)\\.1.kt$"), true);
}
@TestMetadata("effectivePrivate.1.kt")
public void testEffectivePrivate() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/boxInline/private/effectivePrivate.1.kt");
doTestMultiFileWithInlineCheck(fileName);
}
@TestMetadata("kt6453.1.kt")
public void testKt6453() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/boxInline/private/kt6453.1.kt");
@@ -1381,6 +1381,12 @@ public class CompileKotlinAgainstInlineKotlinTestGenerated extends AbstractCompi
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/codegen/boxInline/private"), Pattern.compile("^(.+)\\.1.kt$"), true);
}
@TestMetadata("effectivePrivate.1.kt")
public void testEffectivePrivate() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/boxInline/private/effectivePrivate.1.kt");
doBoxTestWithInlineCheck(fileName);
}
@TestMetadata("kt6453.1.kt")
public void testKt6453() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/boxInline/private/kt6453.1.kt");
@@ -106,6 +106,20 @@ val DeclarationDescriptorWithVisibility.isEffectivelyPublicApi: Boolean
return true
}
val DeclarationDescriptorWithVisibility.isEffectivelyPrivateApi: Boolean
get() {
var parent: DeclarationDescriptorWithVisibility? = this
while (parent != null) {
if (Visibilities.isPrivate(parent.visibility)) return true
parent = DescriptorUtils.getParentOfType(parent, DeclarationDescriptorWithVisibility::class.java)
}
return false
}
val DeclarationDescriptor.isInsidePrivateClass: Boolean
get() {
var parent = containingDeclaration as? ClassDescriptor
@@ -1066,7 +1066,7 @@ fun main(args: Array<String>) {
}
}
internal class TestGroup(val testsRoot: String, val testDataRoot: String) {
private class TestGroup(val testsRoot: String, val testDataRoot: String) {
inline fun <reified T: TestCase> testClass(
suiteTestClass: String = getDefaultSuiteTestClass(T::class.java),
noinline init: TestClass.() -> Unit