[FIR] Add EXPOSED_SUPER_(CLASS/INTERFACE) checker
This commit is contained in:
committed by
Mikhail Glukhikh
parent
ef09850df8
commit
49593d308c
@@ -0,0 +1,63 @@
|
|||||||
|
class A {
|
||||||
|
protected interface AProtectedI {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
interface APublicI {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class B {
|
||||||
|
protected class BProtected {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
inner class BInner {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private class C {
|
||||||
|
class CPublic {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
interface CPublicI {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class D : A {
|
||||||
|
class Test1 : A.AProtectedI {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
interface E {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class Test2 : A.APublicI, B.BInner {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class Test3 : C.CPublicI, <!EXPOSED_SUPER_CLASS!>C<!> {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class Test4 : E, A.AProtectedI {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class Test5 : C.CPublicI, B.BInner {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class Test6 : E, <!EXPOSED_SUPER_CLASS!>C.CPublic<!> {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class Test7 : D.PublicButProtected {
|
||||||
|
|
||||||
|
}
|
||||||
+100
@@ -0,0 +1,100 @@
|
|||||||
|
FILE: exposedSupertype.kt
|
||||||
|
public final class A : R|kotlin/Any| {
|
||||||
|
public constructor(): R|A| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
protected abstract interface AProtectedI : R|kotlin/Any| {
|
||||||
|
}
|
||||||
|
|
||||||
|
public abstract interface APublicI : R|kotlin/Any| {
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class B : R|kotlin/Any| {
|
||||||
|
public constructor(): R|B| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
protected final class BProtected : R|kotlin/Any| {
|
||||||
|
public[protected] constructor(): R|B.BProtected| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public final inner class BInner : R|kotlin/Any| {
|
||||||
|
public constructor(): R|B.BInner| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
private final class C : R|kotlin/Any| {
|
||||||
|
public[private] constructor(): R|C| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
public[private] final class CPublic : R|kotlin/Any| {
|
||||||
|
public[private] constructor(): R|C.CPublic| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public[private] abstract interface CPublicI : R|kotlin/Any| {
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class D : R|A| {
|
||||||
|
public constructor(): R|D| {
|
||||||
|
super<R|A|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
public final class Test1 : R|A.AProtectedI| {
|
||||||
|
public constructor(): R|D.Test1| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public abstract interface E : R|kotlin/Any| {
|
||||||
|
}
|
||||||
|
public final class Test2 : R|A.APublicI|, R|B.BInner| {
|
||||||
|
public constructor(): R|Test2| {
|
||||||
|
super<R|B.BInner|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class Test3 : R|C.CPublicI|, R|C| {
|
||||||
|
public constructor(): R|Test3| {
|
||||||
|
super<R|C|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class Test4 : R|E|, R|A.AProtectedI| {
|
||||||
|
public constructor(): R|Test4| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class Test5 : R|C.CPublicI|, R|B.BInner| {
|
||||||
|
public constructor(): R|Test5| {
|
||||||
|
super<R|B.BInner|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class Test6 : R|E|, R|C.CPublic| {
|
||||||
|
public constructor(): R|Test6| {
|
||||||
|
super<R|C.CPublic|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
public final class Test7 : R|ERROR CLASS: Symbol not found, for `D.PublicButProtected`| {
|
||||||
|
public constructor(): R|Test7| {
|
||||||
|
super<R|kotlin/Any|>()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
Generated
+5
@@ -2168,6 +2168,11 @@ public class FirDiagnosticsTestGenerated extends AbstractFirDiagnosticsTest {
|
|||||||
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/fir/analysis-tests/testData/resolve/visibility"), Pattern.compile("^([^.]+)\\.kt$"), null, true);
|
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/fir/analysis-tests/testData/resolve/visibility"), Pattern.compile("^([^.]+)\\.kt$"), null, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("exposedSupertype.kt")
|
||||||
|
public void testExposedSupertype() throws Exception {
|
||||||
|
runTest("compiler/fir/analysis-tests/testData/resolve/visibility/exposedSupertype.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("exposedFunctionParameterType.kt")
|
@TestMetadata("exposedFunctionParameterType.kt")
|
||||||
public void testExposedFunctionParameterType() throws Exception {
|
public void testExposedFunctionParameterType() throws Exception {
|
||||||
runTest("compiler/fir/analysis-tests/testData/resolve/visibility/exposedFunctionParameterType.kt");
|
runTest("compiler/fir/analysis-tests/testData/resolve/visibility/exposedFunctionParameterType.kt");
|
||||||
|
|||||||
+5
@@ -2168,6 +2168,11 @@ public class FirDiagnosticsWithLightTreeTestGenerated extends AbstractFirDiagnos
|
|||||||
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/fir/analysis-tests/testData/resolve/visibility"), Pattern.compile("^([^.]+)\\.kt$"), null, true);
|
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/fir/analysis-tests/testData/resolve/visibility"), Pattern.compile("^([^.]+)\\.kt$"), null, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("exposedSupertype.kt")
|
||||||
|
public void testExposedSupertype() throws Exception {
|
||||||
|
runTest("compiler/fir/analysis-tests/testData/resolve/visibility/exposedSupertype.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("exposedFunctionParameterType.kt")
|
@TestMetadata("exposedFunctionParameterType.kt")
|
||||||
public void testExposedFunctionParameterType() throws Exception {
|
public void testExposedFunctionParameterType() throws Exception {
|
||||||
runTest("compiler/fir/analysis-tests/testData/resolve/visibility/exposedFunctionParameterType.kt");
|
runTest("compiler/fir/analysis-tests/testData/resolve/visibility/exposedFunctionParameterType.kt");
|
||||||
|
|||||||
+34
-6
@@ -9,12 +9,15 @@ import com.intellij.lang.LighterASTNode
|
|||||||
import com.intellij.openapi.util.Ref
|
import com.intellij.openapi.util.Ref
|
||||||
import com.intellij.psi.PsiElement
|
import com.intellij.psi.PsiElement
|
||||||
import com.intellij.psi.PsiNameIdentifierOwner
|
import com.intellij.psi.PsiNameIdentifierOwner
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassKind
|
||||||
import org.jetbrains.kotlin.fir.*
|
import org.jetbrains.kotlin.fir.*
|
||||||
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.toRegularClass
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticFactory3
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticFactory3
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
|
||||||
import org.jetbrains.kotlin.fir.declarations.*
|
import org.jetbrains.kotlin.fir.declarations.*
|
||||||
|
import org.jetbrains.kotlin.fir.types.ConeClassLikeType
|
||||||
import org.jetbrains.kotlin.fir.types.ConeKotlinType
|
import org.jetbrains.kotlin.fir.types.ConeKotlinType
|
||||||
import org.jetbrains.kotlin.fir.types.FirTypeRef
|
import org.jetbrains.kotlin.fir.types.FirTypeRef
|
||||||
import org.jetbrains.kotlin.fir.types.coneTypeSafe
|
import org.jetbrains.kotlin.fir.types.coneTypeSafe
|
||||||
@@ -23,13 +26,38 @@ import org.jetbrains.kotlin.lexer.KtTokens
|
|||||||
object FirExposedVisibilityChecker : FirDeclarationChecker<FirMemberDeclaration>() {
|
object FirExposedVisibilityChecker : FirDeclarationChecker<FirMemberDeclaration>() {
|
||||||
override fun check(declaration: FirMemberDeclaration, context: CheckerContext, reporter: DiagnosticReporter) {
|
override fun check(declaration: FirMemberDeclaration, context: CheckerContext, reporter: DiagnosticReporter) {
|
||||||
when (declaration) {
|
when (declaration) {
|
||||||
is FirTypeAlias -> checkTypeAlias(declaration, context, reporter)
|
is FirTypeAlias -> checkTypeAlias(declaration, reporter)
|
||||||
is FirProperty -> checkProperty(declaration, context, reporter)
|
is FirProperty -> checkProperty(declaration, reporter)
|
||||||
is FirFunction<*> -> checkFunction(declaration, context, reporter)
|
is FirFunction<*> -> checkFunction(declaration, reporter)
|
||||||
|
is FirRegularClass -> checkSupertypes(declaration, reporter)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun checkTypeAlias(declaration: FirTypeAlias, context: CheckerContext, reporter: DiagnosticReporter) {
|
private fun checkSupertypes(declaration: FirRegularClass, reporter: DiagnosticReporter) {
|
||||||
|
val classVisibility = declaration.firEffectiveVisibility(declaration.session)
|
||||||
|
val supertypes = declaration.superTypeRefs
|
||||||
|
val isInterface = declaration.classKind == ClassKind.INTERFACE
|
||||||
|
for (supertypeRef in supertypes) {
|
||||||
|
val supertype = supertypeRef.coneTypeSafe<ConeClassLikeType>() ?: continue
|
||||||
|
val clazz = supertype.toRegularClass(declaration.session) ?: continue
|
||||||
|
val superIsInterface = clazz.classKind == ClassKind.INTERFACE
|
||||||
|
if (superIsInterface != isInterface) {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
val restricting = supertype.leastPermissiveDescriptor(declaration.session, classVisibility)
|
||||||
|
if (restricting != null) {
|
||||||
|
reporter.reportExposure(
|
||||||
|
if (isInterface) FirErrors.EXPOSED_SUPER_INTERFACE else FirErrors.EXPOSED_SUPER_CLASS,
|
||||||
|
restricting,
|
||||||
|
classVisibility,
|
||||||
|
restricting.firEffectiveVisibility(declaration.session),
|
||||||
|
supertypeRef.source ?: declaration.source
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun checkTypeAlias(declaration: FirTypeAlias, reporter: DiagnosticReporter) {
|
||||||
val expandedType = declaration.expandedConeType
|
val expandedType = declaration.expandedConeType
|
||||||
val typeAliasVisibility = declaration.firEffectiveVisibility(declaration.session)
|
val typeAliasVisibility = declaration.firEffectiveVisibility(declaration.session)
|
||||||
val restricting = expandedType?.leastPermissiveDescriptor(declaration.session, typeAliasVisibility)
|
val restricting = expandedType?.leastPermissiveDescriptor(declaration.session, typeAliasVisibility)
|
||||||
@@ -44,7 +72,7 @@ object FirExposedVisibilityChecker : FirDeclarationChecker<FirMemberDeclaration>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun checkFunction(declaration: FirFunction<*>, context: CheckerContext, reporter: DiagnosticReporter) {
|
private fun checkFunction(declaration: FirFunction<*>, reporter: DiagnosticReporter) {
|
||||||
val functionVisibility = (declaration as FirMemberDeclaration).firEffectiveVisibility(declaration.session)
|
val functionVisibility = (declaration as FirMemberDeclaration).firEffectiveVisibility(declaration.session)
|
||||||
if (declaration !is FirConstructor) {
|
if (declaration !is FirConstructor) {
|
||||||
val restricting = declaration.returnTypeRef.coneTypeSafe<ConeKotlinType>()
|
val restricting = declaration.returnTypeRef.coneTypeSafe<ConeKotlinType>()
|
||||||
@@ -78,7 +106,7 @@ object FirExposedVisibilityChecker : FirDeclarationChecker<FirMemberDeclaration>
|
|||||||
checkMemberReceiver(declaration.receiverTypeRef, declaration as? FirCallableMemberDeclaration<*>, reporter)
|
checkMemberReceiver(declaration.receiverTypeRef, declaration as? FirCallableMemberDeclaration<*>, reporter)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun checkProperty(declaration: FirProperty, context: CheckerContext, reporter: DiagnosticReporter) {
|
private fun checkProperty(declaration: FirProperty, reporter: DiagnosticReporter) {
|
||||||
val propertyVisibility = declaration.firEffectiveVisibility(declaration.session)
|
val propertyVisibility = declaration.firEffectiveVisibility(declaration.session)
|
||||||
val restricting =
|
val restricting =
|
||||||
declaration.returnTypeRef.coneTypeSafe<ConeKotlinType>()?.leastPermissiveDescriptor(declaration.session, propertyVisibility)
|
declaration.returnTypeRef.coneTypeSafe<ConeKotlinType>()?.leastPermissiveDescriptor(declaration.session, propertyVisibility)
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ import org.jetbrains.kotlin.fir.types.ConeKotlinType
|
|||||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||||
import org.jetbrains.kotlin.lexer.KtModifierKeywordToken
|
import org.jetbrains.kotlin.lexer.KtModifierKeywordToken
|
||||||
import org.jetbrains.kotlin.psi.KtParameter
|
import org.jetbrains.kotlin.psi.KtParameter
|
||||||
|
import org.jetbrains.kotlin.psi.KtSuperTypeListEntry
|
||||||
import org.jetbrains.kotlin.psi.KtTypeReference
|
import org.jetbrains.kotlin.psi.KtTypeReference
|
||||||
|
|
||||||
object FirErrors {
|
object FirErrors {
|
||||||
@@ -58,6 +59,8 @@ object FirErrors {
|
|||||||
val EXPOSED_RECEIVER_TYPE by error3<FirSourceElement, KtTypeReference, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
val EXPOSED_RECEIVER_TYPE by error3<FirSourceElement, KtTypeReference, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
||||||
val EXPOSED_PROPERTY_TYPE by error3<FirSourceElement, PsiElement, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
val EXPOSED_PROPERTY_TYPE by error3<FirSourceElement, PsiElement, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
||||||
val EXPOSED_PARAMETER_TYPE by error3<FirSourceElement, KtParameter, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
val EXPOSED_PARAMETER_TYPE by error3<FirSourceElement, KtParameter, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
||||||
|
val EXPOSED_SUPER_INTERFACE by error3<FirSourceElement, KtSuperTypeListEntry, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
||||||
|
val EXPOSED_SUPER_CLASS by error3<FirSourceElement, KtSuperTypeListEntry, FirEffectiveVisibility, DeclarationWithRelation, FirEffectiveVisibility>()
|
||||||
|
|
||||||
val REPEATED_MODIFIER by error1<FirSourceElement, PsiElement, KtModifierKeywordToken>()
|
val REPEATED_MODIFIER by error1<FirSourceElement, PsiElement, KtModifierKeywordToken>()
|
||||||
val REDUNDANT_MODIFIER by error2<FirSourceElement, PsiElement, KtModifierKeywordToken, KtModifierKeywordToken>()
|
val REDUNDANT_MODIFIER by error2<FirSourceElement, PsiElement, KtModifierKeywordToken, KtModifierKeywordToken>()
|
||||||
|
|||||||
@@ -65,7 +65,6 @@ private fun FirMemberDeclaration.containingClass(session: FirSession): FirRegula
|
|||||||
else -> null
|
else -> null
|
||||||
} ?: return null
|
} ?: return null
|
||||||
if (classId.isLocal) return null
|
if (classId.isLocal) return null
|
||||||
val buffer = session.declaredMemberScopeProvider.getClassByClassId(classId)
|
|
||||||
return (session.firSymbolProvider.getClassLikeSymbolByFqName(classId)?.fir as? FirRegularClass)
|
return (session.firSymbolProvider.getClassLikeSymbolByFqName(classId)?.fir as? FirRegularClass)
|
||||||
?: (session.declaredMemberScopeProvider.getClassByClassId(classId) as? FirRegularClass)
|
?: (session.declaredMemberScopeProvider.getClassByClassId(classId) as? FirRegularClass)
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-1
@@ -6,7 +6,7 @@ interface A extends C {
|
|||||||
|
|
||||||
// FILE: B.kt
|
// FILE: B.kt
|
||||||
|
|
||||||
interface B : A {
|
interface B : <!EXPOSED_SUPER_INTERFACE!>A<!> {
|
||||||
fun bar()
|
fun bar()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -6,6 +6,6 @@ class J extends K {
|
|||||||
|
|
||||||
// FILE: K.kt
|
// FILE: K.kt
|
||||||
|
|
||||||
class K : J() {
|
class K : <!EXPOSED_SUPER_CLASS!>J<!>() {
|
||||||
fun bar() {}
|
fun bar() {}
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-1
@@ -12,6 +12,6 @@ class J extends I {
|
|||||||
|
|
||||||
// FILE: K.kt
|
// FILE: K.kt
|
||||||
|
|
||||||
open class K : J() {
|
open class K : <!EXPOSED_SUPER_CLASS!>J<!>() {
|
||||||
fun baz() {}
|
fun baz() {}
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-1
@@ -1,6 +1,6 @@
|
|||||||
// FILE: ExceptionTracker.kt
|
// FILE: ExceptionTracker.kt
|
||||||
|
|
||||||
interface ExceptionTracker : LockBasedStorageManager.ExceptionHandlingStrategy {
|
interface ExceptionTracker : <!EXPOSED_SUPER_INTERFACE!>LockBasedStorageManager.ExceptionHandlingStrategy<!> {
|
||||||
}
|
}
|
||||||
|
|
||||||
// FILE: StorageManager.kt
|
// FILE: StorageManager.kt
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ internal open class Your: My() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// error, public from internal
|
// error, public from internal
|
||||||
open class His: Your() {
|
open class His: <!EXPOSED_SUPER_CLASS!>Your<!>() {
|
||||||
protected open class Nested
|
protected open class Nested
|
||||||
// error, public from internal
|
// error, public from internal
|
||||||
val <!EXPOSED_PROPERTY_TYPE!>x<!> = My()
|
val <!EXPOSED_PROPERTY_TYPE!>x<!> = My()
|
||||||
@@ -21,5 +21,5 @@ open class His: Your() {
|
|||||||
|
|
||||||
internal class Their: His() {
|
internal class Their: His() {
|
||||||
// error, effectively internal from protected
|
// error, effectively internal from protected
|
||||||
class InnerDerived: His.Nested()
|
class InnerDerived: <!EXPOSED_SUPER_CLASS!>His.Nested<!>()
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,10 @@
|
|||||||
|
public open class A {
|
||||||
|
protected open class B
|
||||||
|
}
|
||||||
|
|
||||||
|
public open class C : A() {
|
||||||
|
protected open class D {
|
||||||
|
// internal & protected(in C) <= protected(in A): Ok
|
||||||
|
internal open class E : <!EXPOSED_SUPER_CLASS!>A.B<!>()
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,3 @@
|
|||||||
// FIR_IDENTICAL
|
|
||||||
public open class A {
|
public open class A {
|
||||||
protected open class B
|
protected open class B
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
// From KT-10753
|
// From KT-10753
|
||||||
object My : Inter() {
|
object My : <!EXPOSED_SUPER_CLASS!>Inter<!>() {
|
||||||
fun <!EXPOSED_FUNCTION_RETURN_TYPE!>foo<!>(<!EXPOSED_PARAMETER_TYPE!>arg: Inter<!>): Inter = arg
|
fun <!EXPOSED_FUNCTION_RETURN_TYPE!>foo<!>(<!EXPOSED_PARAMETER_TYPE!>arg: Inter<!>): Inter = arg
|
||||||
val <!EXPOSED_PROPERTY_TYPE!>x<!>: Inter? = null
|
val <!EXPOSED_PROPERTY_TYPE!>x<!>: Inter? = null
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,13 +5,13 @@ open class A {
|
|||||||
}
|
}
|
||||||
public open class C {
|
public open class C {
|
||||||
// protected relative to C, must be an error
|
// protected relative to C, must be an error
|
||||||
protected open class D : B()
|
protected open class D : <!EXPOSED_SUPER_CLASS!>B<!>()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class E : A.C() {
|
class E : A.C() {
|
||||||
// F has invisible grandparent class B (E does not inherit from A)
|
// F has invisible grandparent class B (E does not inherit from A)
|
||||||
class F : A.C.D() {
|
class F : <!EXPOSED_SUPER_CLASS!>A.C.D<!>() {
|
||||||
init {
|
init {
|
||||||
// Invoke function from invisible grandparent
|
// Invoke function from invisible grandparent
|
||||||
foo()
|
foo()
|
||||||
|
|||||||
@@ -1,12 +0,0 @@
|
|||||||
// See KT-9540
|
|
||||||
|
|
||||||
// all protected should have lower bound that is more permissive than private
|
|
||||||
// protected and internal should have lower bound that is more permissive than private
|
|
||||||
open class A {
|
|
||||||
private interface B
|
|
||||||
protected open class C {
|
|
||||||
protected interface D : B
|
|
||||||
internal interface E : B, D
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1,3 +1,4 @@
|
|||||||
|
// FIR_IDENTICAL
|
||||||
// See KT-9540
|
// See KT-9540
|
||||||
|
|
||||||
// all protected should have lower bound that is more permissive than private
|
// all protected should have lower bound that is more permissive than private
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ public abstract class Outer {
|
|||||||
|
|
||||||
class OuterDerived: Outer() {
|
class OuterDerived: Outer() {
|
||||||
// valid, My has better visibility
|
// valid, My has better visibility
|
||||||
protected class His: Outer.My()
|
protected class His: <!EXPOSED_SUPER_CLASS!>Outer.My<!>()
|
||||||
// valid, My and Your have better visibility
|
// valid, My and Your have better visibility
|
||||||
override fun <!EXPOSED_FUNCTION_RETURN_TYPE!>foo<!>(<!EXPOSED_PARAMETER_TYPE!>my: Outer.My<!>) = Outer.Your()
|
override fun <!EXPOSED_FUNCTION_RETURN_TYPE!>foo<!>(<!EXPOSED_PARAMETER_TYPE!>my: Outer.My<!>) = Outer.Your()
|
||||||
}
|
}
|
||||||
@@ -7,7 +7,7 @@ abstract class Outer {
|
|||||||
|
|
||||||
class OuterDerived: Outer() {
|
class OuterDerived: Outer() {
|
||||||
// valid, My has better visibility
|
// valid, My has better visibility
|
||||||
protected class His: Outer.My()
|
protected class His: <!EXPOSED_SUPER_CLASS!>Outer.My<!>()
|
||||||
// valid, My and Your have better visibility
|
// valid, My and Your have better visibility
|
||||||
override fun <!EXPOSED_FUNCTION_RETURN_TYPE!>foo<!>(<!EXPOSED_PARAMETER_TYPE!>my: Outer.My<!>) = Outer.Your()
|
override fun <!EXPOSED_FUNCTION_RETURN_TYPE!>foo<!>(<!EXPOSED_PARAMETER_TYPE!>my: Outer.My<!>) = Outer.Your()
|
||||||
}
|
}
|
||||||
@@ -2,11 +2,11 @@ private interface My
|
|||||||
|
|
||||||
private open class Base
|
private open class Base
|
||||||
|
|
||||||
public interface Your: My {
|
public interface Your: <!EXPOSED_SUPER_INTERFACE!>My<!> {
|
||||||
fun <T: Base> foo(): T
|
fun <T: Base> foo(): T
|
||||||
}
|
}
|
||||||
|
|
||||||
public class Derived<T: My>(<!EXPOSED_PARAMETER_TYPE!>val <!EXPOSED_PROPERTY_TYPE!>x<!>: My<!>): Base() {
|
public class Derived<T: My>(<!EXPOSED_PARAMETER_TYPE!>val <!EXPOSED_PROPERTY_TYPE!>x<!>: My<!>): <!EXPOSED_SUPER_CLASS!>Base<!>() {
|
||||||
|
|
||||||
constructor(<!EXPOSED_PARAMETER_TYPE!>xx: My?<!>, <!EXPOSED_PARAMETER_TYPE!>x: My<!>): this(xx ?: x)
|
constructor(<!EXPOSED_PARAMETER_TYPE!>xx: My?<!>, <!EXPOSED_PARAMETER_TYPE!>x: My<!>): this(xx ?: x)
|
||||||
|
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ abstract class Your {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// invalid, List<My> is effectively internal
|
// invalid, List<My> is effectively internal
|
||||||
interface His: List<My>
|
interface His: <!EXPOSED_SUPER_INTERFACE!>List<My><!>
|
||||||
|
|
||||||
// invalid, My is internal
|
// invalid, My is internal
|
||||||
interface Generic<E: My>
|
interface Generic<E: My>
|
||||||
|
|||||||
+1
-1
@@ -14,4 +14,4 @@ package a
|
|||||||
import pack1.*
|
import pack1.*
|
||||||
import pack2.*
|
import pack2.*
|
||||||
|
|
||||||
class X : <!INAPPLICABLE_CANDIDATE!>SomeClass<!>()
|
class X : <!EXPOSED_SUPER_CLASS, INAPPLICABLE_CANDIDATE!>SomeClass<!>()
|
||||||
|
|||||||
@@ -17,5 +17,5 @@ package a
|
|||||||
import pack1.SomeClass.*
|
import pack1.SomeClass.*
|
||||||
import pack2.*
|
import pack2.*
|
||||||
|
|
||||||
class X : <!INAPPLICABLE_CANDIDATE!>N<!>()
|
class X : <!EXPOSED_SUPER_CLASS, INAPPLICABLE_CANDIDATE!>N<!>()
|
||||||
class Y : PublicNested()
|
class Y : PublicNested()
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ fun test() {
|
|||||||
xx = 40
|
xx = 40
|
||||||
}
|
}
|
||||||
|
|
||||||
class B : <!INAPPLICABLE_CANDIDATE!>A<!>() {}
|
class B : <!EXPOSED_SUPER_CLASS, INAPPLICABLE_CANDIDATE!>A<!>() {}
|
||||||
|
|
||||||
class Q {
|
class Q {
|
||||||
class W {
|
class W {
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ fun test() {
|
|||||||
val po = <!INAPPLICABLE_CANDIDATE!>PO<!>
|
val po = <!INAPPLICABLE_CANDIDATE!>PO<!>
|
||||||
}
|
}
|
||||||
|
|
||||||
class B : <!INAPPLICABLE_CANDIDATE!>A<!>() {}
|
class B : <!EXPOSED_SUPER_CLASS, INAPPLICABLE_CANDIDATE!>A<!>() {}
|
||||||
|
|
||||||
class Q {
|
class Q {
|
||||||
class W {
|
class W {
|
||||||
|
|||||||
@@ -36,7 +36,7 @@ fun test() {
|
|||||||
val po = <!INAPPLICABLE_CANDIDATE!>PO<!>
|
val po = <!INAPPLICABLE_CANDIDATE!>PO<!>
|
||||||
}
|
}
|
||||||
|
|
||||||
class B : <!INAPPLICABLE_CANDIDATE!>A<!>() {}
|
class B : <!EXPOSED_SUPER_CLASS, INAPPLICABLE_CANDIDATE!>A<!>() {}
|
||||||
|
|
||||||
class Q {
|
class Q {
|
||||||
class W {
|
class W {
|
||||||
|
|||||||
Reference in New Issue
Block a user