Skip to content

Commit cbef025

Browse files
committed
Allow to turn the first parameter of a SAM-converted lambda into the receiver (KT-12848)
1 parent fc8cc21 commit cbef025

File tree

57 files changed

+935
-148
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

57 files changed

+935
-148
lines changed

.idea/artifacts/KotlinPlugin.xml

+107-101
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

.idea/modules.xml

+2
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

build.xml

+25-2
Original file line numberDiff line numberDiff line change
@@ -865,6 +865,29 @@
865865
<fileset dir="${basedir}/plugins/noarg/noarg-cli/src" includes="META-INF/services/**"/>
866866
</jar>
867867
</target>
868+
869+
<target name="sam-with-receiver-compiler-plugin">
870+
<cleandir dir="${output}/classes/sam-with-receiver-compiler-plugin"/>
871+
<javac2 destdir="${output}/classes/sam-with-receiver-compiler-plugin" debug="true" debuglevel="lines,vars,source" includeAntRuntime="false">
872+
<withKotlin modulename="noarg">
873+
<compilerarg value="-version"/>
874+
</withKotlin>
875+
<skip pattern="kotlin/Metadata"/>
876+
<src>
877+
<pathelement path="plugins/sam-with-receiver/src"/>
878+
</src>
879+
<classpath>
880+
<pathelement path="${idea.sdk}/core/intellij-core.jar"/>
881+
<pathelement path="${kotlin-home}/lib/kotlin-compiler.jar"/>
882+
</classpath>
883+
</javac2>
884+
885+
<jar destfile="${kotlin-home}/lib/sam-with-receiver-compiler-plugin.jar">
886+
<fileset dir="${output}/classes/sam-with-receiver-compiler-plugin"/>
887+
<zipfileset file="${kotlin-home}/build.txt" prefix="META-INF"/>
888+
<fileset dir="${basedir}/plugins/sam-with-receiver/src" includes="META-INF/services/**"/>
889+
</jar>
890+
</target>
868891

869892
<target name="annotation-processing-under-jdk8">
870893
<property environment="env"/>
@@ -1273,11 +1296,11 @@
12731296
depends="builtins,stdlib,kotlin-test,core,reflection,pack-runtime,pack-runtime-sources,script-runtime,mock-runtime-for-test"/>
12741297

12751298
<target name="dist"
1276-
depends="clean,init,prepare-dist,preloader,runner,serialize-builtins,compiler,compiler-sources,kotlin-build-common,ant-tools,runtime,kotlin-js-stdlib,android-extensions-compiler,allopen-compiler-plugin,noarg-compiler-plugin,annotation-processing-under-jdk8,daemon-client,kotlin-build-common-test"
1299+
depends="clean,init,prepare-dist,preloader,runner,serialize-builtins,compiler,compiler-sources,kotlin-build-common,ant-tools,runtime,kotlin-js-stdlib,android-extensions-compiler,allopen-compiler-plugin,noarg-compiler-plugin,sam-with-receiver-compiler-plugin,annotation-processing-under-jdk8,daemon-client,kotlin-build-common-test"
12771300
description="Builds redistributables from sources"/>
12781301

12791302
<target name="dist-quick"
1280-
depends="clean,init,prepare-dist,preloader,serialize-builtins,compiler-quick,ant-tools,runtime,kotlin-js-stdlib,android-extensions-compiler,allopen-compiler-plugin,noarg-compiler-plugin,annotation-processing-under-jdk8"
1303+
depends="clean,init,prepare-dist,preloader,serialize-builtins,compiler-quick,ant-tools,runtime,kotlin-js-stdlib,android-extensions-compiler,allopen-compiler-plugin,noarg-compiler-plugin,sam-with-receiver-compiler-plugin,annotation-processing-under-jdk8"
12811304
description="Builds everything, but classes are reused from project out dir, doesn't run proguard and javadoc"/>
12821305

12831306
<target name="dist-quick-compiler-only"

compiler/frontend.java/src/org/jetbrains/kotlin/frontend/java/di/injection.kt

+3-1
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ import org.jetbrains.kotlin.load.java.JavaClassFinderImpl
3333
import org.jetbrains.kotlin.load.java.components.*
3434
import org.jetbrains.kotlin.load.java.lazy.ModuleClassResolver
3535
import org.jetbrains.kotlin.load.java.sam.SamConversionResolverImpl
36+
import org.jetbrains.kotlin.load.java.sam.SamWithReceiverResolver
3637
import org.jetbrains.kotlin.load.kotlin.DeserializationComponentsForJava
3738
import org.jetbrains.kotlin.load.kotlin.JvmVirtualFileFinderFactory
3839
import org.jetbrains.kotlin.platform.JvmBuiltIns
@@ -68,7 +69,8 @@ fun StorageComponentContainer.configureJavaTopDownAnalysis(
6869
useImpl<TraceBasedErrorReporter>()
6970
useImpl<PsiBasedExternalAnnotationResolver>()
7071
useImpl<JavaPropertyInitializerEvaluatorImpl>()
71-
useInstance(SamConversionResolverImpl)
72+
useImpl<SamWithReceiverResolver>()
73+
useImpl<SamConversionResolverImpl>()
7274
useImpl<JavaSourceElementFactoryImpl>()
7375
useInstance(InternalFlexibleTypeTransformer)
7476

compiler/frontend.java/src/org/jetbrains/kotlin/load/java/sam/SamConversionResolverImpl.kt

+9-3
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,10 @@ import org.jetbrains.kotlin.load.java.descriptors.JavaClassConstructorDescriptor
2525
import org.jetbrains.kotlin.load.java.descriptors.JavaMethodDescriptor
2626
import org.jetbrains.kotlin.load.java.descriptors.SamConstructorDescriptor
2727
import org.jetbrains.kotlin.load.java.lazy.descriptors.LazyJavaClassDescriptor
28+
import org.jetbrains.kotlin.storage.StorageManager
2829
import org.jetbrains.kotlin.types.SimpleType
2930

30-
object SamConversionResolverImpl : SamConversionResolver {
31+
class SamConversionResolverImpl(val storageManager: StorageManager, val samWithReceiverResolver: SamWithReceiverResolver): SamConversionResolver {
3132
override fun resolveSamConstructor(constructorOwner: DeclarationDescriptor, classifier: () -> ClassifierDescriptor?): SamConstructorDescriptor? {
3233
val classifierDescriptor = classifier()
3334
if (classifierDescriptor !is LazyJavaClassDescriptor || classifierDescriptor.functionTypeForSamInterface == null) return null
@@ -44,8 +45,13 @@ object SamConversionResolverImpl : SamConversionResolver {
4445
}
4546
}
4647

48+
private val functionTypesForSamInterfaces = storageManager.createCacheWithNullableValues<JavaClassDescriptor, SimpleType>()
49+
4750
override fun resolveFunctionTypeIfSamInterface(classDescriptor: JavaClassDescriptor): SimpleType? {
48-
val abstractMethod = SingleAbstractMethodUtils.getSingleAbstractMethodOrNull(classDescriptor) ?: return null
49-
return SingleAbstractMethodUtils.getFunctionTypeForAbstractMethod(abstractMethod)
51+
return functionTypesForSamInterfaces.computeIfAbsent(classDescriptor) {
52+
val abstractMethod = SingleAbstractMethodUtils.getSingleAbstractMethodOrNull(classDescriptor) ?: return@computeIfAbsent null
53+
val shouldConvertFirstParameterToDescriptor = samWithReceiverResolver.shouldConvertFirstSamParameterToReceiver(abstractMethod)
54+
SingleAbstractMethodUtils.getFunctionTypeForAbstractMethod(abstractMethod, shouldConvertFirstParameterToDescriptor)
55+
}
5056
}
5157
}

0 commit comments

Comments
 (0)